在我的应用程序的主页中,我迭代了一组网球运动员(public class Email extends AbstractDatabaseEntity<Long> {
private String email;
protected Email() {
}
public String getEmail() {
return email;
}
private void setEmail(final String email) {
this.email = email;
}
public static final class Builder extends AbstractEntityBuilder<Email> {
private Builder(Email entity, EntityState state) {
super(entity, state);
}
public static Builder create() {
return new Builder(new Email(), EntityState.NEW);
}
public static Builder from(Email entity) {
return new Builder(entity, EntityState.BUILT);
}
public Builder email(String email) {
entity.setEmail(email);
return this;
}
}
}
public abstract class AbstractEntityBuilder<T extends Object> {
protected final EntityState state;
protected T entity;
...
}
),并为每个网球运动员创建一个包含其属性的表格行和一个允许当前用户登记的网球运动员:
@atp_ranks
为了让用户有机会立即看到提交表单的结果,我在每个表单中添加了<table>
<thead>
<tr>
<th> Rank </th>
<th> Player </th>
<th> Points </th>
<th id="atp_count" class="tennis_stats"> <%= current_user.atp_ranks.count %> selected </th>
</tr>
</thead>
<tbody>
<% @atp_ranks.each do |tennis_player| %>
<tr id="tennist-<%= tennis_player.ranking %>">
<td class="atpranking"> <%= tennis_player.ranking %> </td>
<td class="atpname"> <%= tennis_player.name %> </td>
<td class="atppoints"> <%= tennis_player.points %> </td>
<% unless Time.now.month == 12 %>
<td>
<div id="atpenlist_form_<%= tennis_player.id %>">
<% if current_user.atpenlisted?(tennis_player) %>
<%= form_for(current_user.atp_selections.find_by(atp_rank_id: tennis_player.id), html: { method: :delete }, remote: true) do |f| %>
<%= f.submit "Dump", class: "btn btn-warning btn-sm" %>
<% end %>
<% else %>
<%= form_for(current_user.atp_selections.build, remote: true) do |f| %>
<div><%= hidden_field_tag :atp_id, tennis_player.id %></div>
<%= f.submit "Choose", class: "btn btn-primary btn-sm" %>
<% end %>
<% end %>
</div>
</td>
<% end %>
</tr>
<% end %>
</tbody>
</table>
,并将这些表单保存为remote: true
中的部分内容。
然后我在上面的目录中创建了app/views/atp_selections
和create.js.erb
个文件。以下是destroy.js.erb
文件的内容:
create.js.erb
jQuery代码应该操纵$("#atp_count").html('<%= current_user.atp_ranks.count %> selected');
$("#atpenlist_form_<%= @tennist.id %>").html("<%= escape_javascript(render('atp_selections/atpdiscard')) %>");
id和atp_count
id,即第四个atpenlist_form_<%= @tennist.id %>
标记的id,以及th
的id包含按钮的形式。
以下是我的div
控制器的摘录,该控制器太长而无法完全报告:
atp_selections
如您所见, def create
@tennist = AtpRank.find(params[:atp_id])
rankings = current_user.atp_ranks.pluck(:ranking)
atp_selections = current_user.atp_selections
wta_selections = current_user.wta_selections
if atp_selections.count <= 15 && wta_selections.count < 16
if (1..5).include?(@tennist.ranking) && (rankings & (1..5).to_a).size == 0
current_user.atpenlist(@tennist)
respond_to do |format|
format.html { redirect_to root_url }
format.js
end
elsif (6..15).include?(@tennist.ranking) && (rankings & (6..15).to_a).size < 3
current_user.atpenlist(@tennist)
respond_to do |format|
format.html { redirect_to root_url }
format.js
end
...
控制器的创建操作由多个响应登记规则的if-else语句组成。但是,重要的是,在每种情况下,我都使用atp_selections
方法包含了所需的代码,以便Ajax处理请求。
但是,控制器不响应Ajax,只有在页面刷新后才能看到对respond_to
和atp_count
的更改。
rails控制台报告以下错误:
atpenlist_form_<%= @tennist.id %>
Rendered atp_selections/create.js.erb (223.6ms)
Completed 500 Internal Server Error in 695ms (ActiveRecord: 83.2ms)
ActionView::Template::Error (undefined local variable or method `tennis_player' for #<#<Class:0x00000005948748>:0x0000000593f648>):
1: <%= form_for(current_user.atp_selections.find_by(atp_rank_id: tennis_player.id),
2: html: { method: :delete }, remote: true) do |f| %>
3: <%= f.submit "Dump", class: "btn btn-warning btn-sm" %>
4: <% end %>
app/views/atp_selections/_atpdiscard.html.erb:1:in `_app_views_atp_selections__atpdiscard_html_erb__451019467450256030_46643760'
app/views/atp_selections/create.js.erb:2:in `_app_views_atp_selections_create_js_erb__4477173780394533370_46811020'
是迭代的变量,从渲染的部分导入时似乎不接受它。
答案 0 :(得分:1)
当您从 js.erb 文件中调用相同的部分时,未声明tennis_player
,因此您将获得错误未定义变量。
所以你需要将 @tennist 作为 tennis_player 传递到create.js.erb
的部分
$("#atpenlist_form_<%= @tennist.id %>").html("<%= j render 'atp_selections/atpdiscard', locals: {tennis_player: @tennist} %>");