建立带有两个外键的关联时出错

时间:2018-07-30 02:24:46

标签: ruby-on-rails associations

我有一个用户和推荐模型。用户有几种帐户类型:学生,管理员,推荐人等。学生用户可以分配推荐人来提交推荐。我没有使用Rolify,所以

我目前有:

class Recommendation < ApplicationRecord
  belongs_to :assigner, class_name: "User", foreign_key: "user_id"
  belongs_to :writer,   class_name: "User", foreign_key: "writer_id"
end

class User < ApplicationRecord
  has_many :recommendations_via_assigning, class_name: "Recommendation", foreign_key: :assigner_id
  has_many :recommendations_via_writing,   class_name: "Recommendation", foreign_key: :writer_id
end

class CreateRecommendations < ActiveRecord::Migration[5.1]
  def change
    create_table :recommendations do |t|
      t.integer :writer_id, foreign_key: true
      t.integer :assigner_id, foreign_key: true
      t.text    :text

      t.timestamps
    end

    add_index :recommendations, :writer_id
    add_index :recommendations, :assigner_id
  end
end

控制器

 def new
   @recommendation = current_user.recommendations_via_assigning.build
 end

 def create
   @recommendation = current_user.recommendations_via_assigning.build(recommendation_request_params)
   if @recommendation.save
     @recommendation.send_invitation_email
     flash[:info] = "An email with submission instructions has been sent to the recommender you have invited."
     redirect_to user_url
   else
     render 'new'
   end
 end

 private
    def recommendation_request_params
     params.require(:recommendation).permit(:assigner_id, :first_name, :last_name, :email, :relationship)
   end

   def recommendation_content_params
     params.require(:recommendation).permit(:writer_id, :first_name, :last_name, :email, :text)
   end

我无法保存推荐,因为它需要writer_id,在提交Recommendation#create时将不知道该推荐。需要发生的是,将一封电子邮件发送到所提供的电子邮件地址,邀请教师创建一个帐户,并在注册该帐户后,通过ID与教师帐户的writer_id进行推荐。

如何修改现有代码,以使我可以在没有writer_id的情况下通过Recommendation#create?

2 个答案:

答案 0 :(得分:2)

首先正确声明外键:

class CreateRecommendations < ActiveRecord::Migration[5.0]
  def change
    create_table :recommendations do |t|
      t.belongs_to :writer, foreign_key: { to_table: :users }
      t.belongs_to :assigner, foreign_key: { to_table: :users }

      t.timestamps
    end
  end
end

当外键约束不能从列名派生时,您需要为其手动指定引用表。

您还需要将关联设置为可选以删除验证:

class Recommendation < ApplicationRecord
  belongs_to :assigner, class_name: "User", 
                        foreign_key: "user_id"
  belongs_to :writer,   class_name: "User", 
                        foreign_key: "writer_id",
                        optional: true
end

答案 1 :(得分:1)

Read here

您需要将belongs_to关联设为可选:

belongs_to :writer, class_name: "User", foreign_key: "writer_id", optional: true