首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Rails 5为文章和评论添加点赞

Rails 5为文章和评论添加点赞
EN

Stack Overflow用户
提问于 2018-08-20 10:14:41
回答 1查看 804关注 0票数 0

在Rails5中,我尝试在不依赖gem的情况下从头开始添加Like。我差一点就把它写下来了,但当涉及到评论时,我完全被所发生的事情难住了。

存储和保存article.likes的效果非常好。然后我让comment.likes开始工作了。现在,当我喜欢一条评论时,他们会单独存储一个新的赞(太棒了!),除了Now文章没有正确地保存任何赞,更奇怪的是: article.likes.count给出了所有评论的赞的总和。我相信这是一个很容易解决的问题,但我只是完全错过了它,我已经尝试了所有的方法。为了这个我已经下了很深的兔子洞。

我认为问题出在路由,或者模型之间的关联上。

文章有很多评论,两篇文章都有很多赞。以下是以like.rb开头的模型:

代码语言:javascript
复制
 class Like < ApplicationRecord
   belongs_to :user
   belongs_to :article
   belongs_to :comment

   # Make sure that one user can only have one like per post or comment
   validates :user_id, uniqueness: { scope: [:article_id, :comment_id] }

 end

article.rb

代码语言:javascript
复制
class Article < ApplicationRecord

  belongs_to :user

  ...

  # destroy associated comments on article deletion
  has_many :comments, dependent: :destroy

  has_many :likes, dependent: :destroy

end

comment.rb

代码语言:javascript
复制
class Comment < ApplicationRecord
  belongs_to :article
  belongs_to :user

  ...

  has_many :likes, dependent: :destroy

end

routes.rb

代码语言:javascript
复制
  ...
  resources :articles, :path => 'blog' do
    resources :likes, only: [:create, :destroy]

    resources :comments do
      resources :likes, only: [:create, :destroy]
    end

  end

多肉的likes_controller.rb。注意#{},一切都按它应该的方式进行了检查,那么为什么comment.likes.create可以正确保存,而article.likes.create却不能呢?请帮帮忙。

代码语言:javascript
复制
class LikesController < ApplicationController
  before_action :get_signed_in_user
  before_action :comment_or_article

  def create
    if @comment_like
      like_resource(comment)
    else
      like_resource(article)
    end
  end

  def destroy
    if @comment_like
      comment.likes.where(user: current_user).destroy_all
    else
      article.likes.where(user: current_user).destroy_all
    end
    flash[:success] = "Unliked! :("
    redirect_to article_redirect(article)
  end

  private
  def like_resource(obj)
    if obj.likes.where(user: current_user.id).present?
      flash[:error] = "You've already upvoted this! + #{like_params} + #{@comment_like} + #{obj}"
    if @comment_like
      if obj.likes.create(user: current_user, article: @article)
        flash[:success] = "Upvoted Comment! + #{like_params} + #{@comment_like} + #{obj}"
      else
          flash[:error] = "An error prevented you from upvoting."
      end
    elsif obj.likes.create(user: current_user)
      flash[:success] = "Upvoted Blog! + #{like_params} + #{@comment_like} + #{obj}"
    else
      flash[:error] = "An error prevented you from upvoting."
    end
    redirect_to article_path(article)
  end

  def get_signed_in_user
    unless user_signed_in?
      flash[:error] = "Sign in to upvote!"
      redirect_back(fallback_location: articles_path)
    end
  end

  # decide what we are liking
  def comment_or_article
    if comment
      @comment_like = true
    else
      @comment_like = false
    end
  end

  def article
    @article = Article.find(params[:article_id])
  end

  def comment
    unless params[:comment_id].nil?
      @comment = article.comments.find(params[:comment_id])
    end
  end

  def like_params
    params.permit( :article_id, :comment_id).merge(user_id: current_user.id)
  end
end

最后,我的文章/show.html.erb中的like按钮:

代码语言:javascript
复制
<%= link_to "Like", article_likes_path(@article), method: :post %>
<%= "#{@article.likes.count}" %>

... # inside loop to show comments:
<%= link_to "Like", article_comment_likes_path(@article, comment), method: :post %>
<%= "#{comment.likes.count}" %>

TLDR:评论喜欢工作很好,保存很好,单独计算很好。文章点赞不保存,但article.likes.count === article.comments.likes.count。为什么?我希望article.likes是完全独特的,就像它自己的评论一样。

提前谢谢你。

编辑:去掉like.rb中的belongs_to :comments并重构like_controller.rb main函数以

代码语言:javascript
复制
 private
  def like_resource(obj)
    if obj.likes.where(user: current_user.id).present?
      flash[:error] = "You've already upvoted this!"
    elsif obj.likes.create(user: current_user, article: @article)
      flash[:success] = "Upvoted!"
    else
      flash[:error] = "An error prevented you from upvoting."
    end
    redirect_to article_path(article)
  end

喜欢评论时,总是提供@文章会很有帮助。像这样的文章不需要comment_id来保存。

很抱歉发了这么长的帖子,希望这能对某些人有所帮助。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-08-20 10:33:56

实际上,我刚刚想通了。

代码语言:javascript
复制
class Like < ApplicationRecord
  belongs_to :user
  belongs_to :article
  # belongs_to :comment
end

注释掉上面的内容后,它允许在不引用注释的情况下保存@文章"like“。文章点赞被正确地保存。但是,每当喜欢article.comment时,article.likes.count仍然会递增。这意味着article.likes总是>= article.comments.likes;这是完全没问题的。

我刚刚将@article.likes更改为:

代码语言:javascript
复制
  <%= "#{@article.likes.where(comment_id: nil).count}" %>

过滤掉所有严格的article.likes。comment.likes仍然可以完美地工作。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/51923385

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档