Rails - 在具有多个部分的页面上更新单个部分

时间:2013-10-19 17:52:58

标签: ruby-on-rails ajax partial voting

我有一个包含多个帖子的页面。我希望每个帖子的投票在用户投票后更新,而不必重新加载页面。我看了看,但是大多数遇到这个问题的人在页面上只有一个部分,所以他们只能使用部分包含div的id。

我尝试过使用Ajax和jQuery,但一直遇到问题。现在,投票正确更新,但它改变了一个链接上的所有部分。我已经尝试为每个部分设置动态ID,但它只更改第一个部分,因为@post变量被设置为最后一个帖子。所以,即使我在第三篇文章中投票,第一篇帖子的部分内容也会改变,而不是第三篇。

我在rails 3.2.14和ruby 2.0

这是我的代码:

文章/ index.html.erb

<% all_posts.each do |post| %>
  <div class="votes-box">
    <%= render partial: 'vote', locals: {post: post}  %>
  </div>
<% end %>

文章/ _vote.html.erb

 <%= link_to '', vote_post_path(post, type: 'up' ), remote: true, method: 'post', class: 'upvote' %>
 <div class="vote-rep"><%= post.reputation_for(:votes).to_i %> Rep</div>
 <%= link_to '', vote_post_path(post, type: 'down' ), remote: true, method: 'post', class: 'downvote' %>

vote.js.erb

$(".votes-box").html("<%= escape_javascript(render partial: 'vote', locals: {post: @post}).html_safe %>");

posts_controller.rb

def vote
  value = params[:type] == 'up' ? 1 : -1
  @post = Post.find(params[:id])
  @post.add_or_update_evaluation(:votes, value, current_user)
  respond_to do |format| 
    format.js
  end
end

1 个答案:

答案 0 :(得分:1)

关键是首先在html中为每个帖子添加id,然后只在js响应中更新所需的id。

首先是模板

<% all_posts.each do |post| %>
  <%# Or you can use `content_tag_for` %>
  <%# in following line to generate id automatically. %>
  <div id="post_#{post.id}">
    <div class="votes-box">
      <%= render partial: 'vote', locals: {post: post}  %>
    </div>
  </div>
<% end %>

然后回应js

$("#post_#{post.id} .votes-box").html("<%= escape_javascript(render partial: 'vote', 
                                          locals: {post: @post}).html_safe %>");