Ruby-on-rails 为 Rails 模型定义外键关系

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/904421/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-02 21:17:04  来源:igfitidea点击:

Defining foreign key relationships for Rails' models

ruby-on-railsforeign-keys

提问by pez_dispenser

I have a Comment class with a :foreign_key of post_id in the Post class.

我在 Post 类中有一个带有 post_id 的 :foreign_key 的 Comment 类。

class Comment < ActiveRecord::Base
  belongs_to :post, :class_name => "Post", :foreign_key => "post_id", :counter_cache => true
  belongs_to :author, :class_name => "User", :foreign_key => "author_id"
end

But my CreateComments migration does not define a database-level foreign key:

但是我的 CreateComments 迁移没有定义数据库级别的外键:

class CreateComments < ActiveRecord::Migration
  def self.up
    create_table :comments do |t|
      t.column "post_id",       :integer,   :default => 0, :null => false
      t.column "author",        :string,    :default => "",   :limit => 25, :null => false
      t.column "author_email",  :string,    :default => "",   :limit => 50, :null => false
      t.column "content",       :text,      :null => false
      t.column "status",        :string,    :default => "",   :limit => 25, :null => false
      t.timestamps
    end
  end

  def self.down
    drop_table :comments
  end
end

Instead post_id is a simple Integer column.

而 post_id 是一个简单的整数列。

So, it seems that this foreign key relationship exists only in the mind of Rails, not at the database level.

所以,这个外键关系似乎只存在于Rails的脑海中,而不存在于数据库层面。

Is this correct?

这样对吗?

Also, is it necessary for the corresponding Post model to also declare its reciprocal foreign key relationship with Comments using the :foreign_key attribute or could that be omitted?

此外,相应的 Post 模型是否有必要使用 :foreign_key 属性声明其与 Comments 的相互外键关系,或者可以省略吗?

class Post < ActiveRecord::Base
  set_table_name("blog_posts")
  belongs_to :author, :class_name => "User", :foreign_key => 'author_id'
  has_many :comments, :class_name => "Comment",
    :foreign_key => 'post_id', :order => "created_at desc", :dependent => :destroy
  has_many :categorizations
  has_many :categories, :through => :categorizations
  named_scope :recent, :order => "created_at desc", :limit => 5

end

回答by John Topley

The Rails default behaviour is that the column used to hold the foreign key on a model is the name of the association with the suffix _idadded. The :foreign_keyoption lets you set the name of the foreign key directly. The associations between your Postand Commentmodel classes should look like this:

Rails 的默认行为是模型上用于保存外键的列是_id添加后缀的关联名称。该:foreign_key选项允许您直接设置外键的名称。您的PostComment模型类之间的关联应如下所示:

class Post < ActiveRecord::Base
  has_many :comments
end

class Comment < ActiveRecord::Base
  belongs_to :post
end

—Note that you don't need :class_name => "Post"in your Commentmodel. Rails already has that information. You should only be specifying :class_nameand :foreign_keywhen you need to override the Rails' conventions.

- 请注意:class_name => "Post",您的Comment模型中不需要。Rails 已经有了这些信息。您应该只被指定:class_name:foreign_key当你需要重写Rails的约定。

You're correct that Rails maintains the foreign key relationships for you. You can enforce them in the database layer if you want by adding foreign key constraints.

您是正确的,Rails 为您维护外键关系。如果需要,您可以通过添加外键约束在数据库层强制执行它们。