【问题标题】:rails multiple belongs_to assignments with nested attributesrails 具有嵌套属性的多个 belongs_to 分配
【发布时间】:2023-03-07 22:15:01
【问题描述】:

我的问题是如何使用嵌套属性分配多个 belongs_to 关联?

我想建立一个问题系统。当我创建问题时,我还想创建第一条评论作为问题正文。

所以,我有以下模型:

class Issue < ActiveRecord::Base
  has_many :comments, as: :commentable

  validates :title, presence: true

  accepts_nested_attributes_for :comments
end

class Comment < ActiveRecord::Base
  belongs_to :user
  belongs_to :commentable, polymorphic: true

  validates :content, :user, presence: true
end

我的 IssuesController 如下:

class IssuesController < ApplicationController
  before_action :authenticate_user! #devise authentication

  def new
    @issue = Issue.new
    @issue.comments.build
  end

  def create
    @issue = Issue.new(issue_params)
    @issue.save
  end

  private

  def issue_params
    params.require(:issue).permit(:title, comments_attributes: [:content])
  end
end

以下是我的表单(使用带有 simple_form 和nested_form gems 的苗条模板):

= simple_nested_form_for @issue do |f|

  = f.input :title

  = f.fields_for :comments do |cf|
    = cf.input :content

  = f.button :submit

在这种情况下,我不知道如何将current_user 分配给嵌套属性创建的评论。

有什么建议或其他方法吗?谢谢!

【问题讨论】:

  • 在 cmets 部分中名为 :user 的隐藏字段?
  • 我已经尝试过这种方法,并且有效。但我认为它不安全。
  • 不安全是什么意思?害怕用户摆弄这个领域?然后在控制器中进行。构建评论时,将当前用户作为属性传递,并在创建时再次检查。
  • 你的意思是这样的:@issue.comments.each {|c| c.user = current_user}?
  • 差不多。但这会将每个评论设置为当前用户。不确定这是否是您的预期行为。

标签: ruby-on-rails nested-attributes belongs-to


【解决方案1】:

正如我在 cmets 中所写,有两种方法可以做到这一点。 第一种方法是在你的子表单中添加一个隐藏字段来设置当前用户:

= simple_nested_form_for(@issue) do |f|
  = f.input :title
  = f.fields_for(:comments) do |cf|
    = cf.input(:content)
    = cf.hidden(:user, current_user)
  = f.submit

如果您不相信这种方法,因为担心您的用户会摆弄浏览器中的字段,您也可以在控制器中执行此操作。

class IssuesController < ApplicationController
  before_action :authenticate_user! #devise authentication

  def new
    @issue = Issue.new
    @issue.comments.build
  end

  def create
    @issue = Issue.new(issue_params)
    @issue.comments.first.user = current_user
    @issue.save
  end

  private

  def issue_params
    params.require(:issue).permit(:title, comments_attributes: [:content])
  end
end

这样,您可以获取通过表单创建的第一条评论,然后手动将用户分配给它。然后您就可以确定第一个创建的评论属于您当前的用户。

【讨论】:

    【解决方案2】:

    您也可以在使用参数时将user_id 添加为current_user.id

    class IssuesController < ApplicationController
      before_action :authenticate_user! #devise authentication
    
      def new
        @issue = Issue.new
        @issue.comments.build
      end
    
      def create
        @issue = Issue.new(issue_params)
        @issue.save
      end
    
      private
    
      def issue_params
        params[:issue][:comment][:user_id] = current_user.id
        params.require(:issue).permit(:title, comments_attributes: [:content, :user_id])
      end
    end
    

    【讨论】:

    • 这意味着我需要向问题模型添加“评论”方法或关联?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多