Sql 使外键也成为Rails迁移中的主键

Sql 使外键也成为Rails迁移中的主键,sql,ruby-on-rails,database,ruby-on-rails-4,rails-migrations,Sql,Ruby On Rails,Database,Ruby On Rails 4,Rails Migrations,编辑: 从Rails的角度来看,我希望列是主键和外键。也就是说,使用引用方法的外键。我想做一些类似的事情: def change create_table :VipPerson, id: false do |t| t.primary_key :person_id t.references :person, :id, column: :person_id t.timestamps end end 我想要一个自定义主键,Rails模型也使用它来指向Person模型

编辑:

从Rails的角度来看,我希望列是主键和外键。也就是说,使用
引用
方法的外键。我想做一些类似的事情:

def change
  create_table :VipPerson, id: false do |t|
    t.primary_key :person_id
    t.references :person, :id, column: :person_id

    t.timestamps
  end
end
我想要一个自定义主键,Rails模型也使用它来指向Person模型(见下文)。这实际上与sql数据库使用的外键无关(正如Demi Magus所指出的,Rails直到Rails 4.2才支持创建真正的外键)

-

我希望在Rails项目中实现多表交互(MTI),从而实现继承,就像在关系数据库中通常所做的那样:

table: Person
-------------
(PK) ID
Name
...

table: VipPerson (specalization of Person)
----------------
(PK) (FK) Person_ID
VIP-Status
...
为此,我需要编写一个迁移,将一个属性(这里
Person\u ID
)同时声明为(自定义)主键和外键。我不知道如何使用Rails的迁移方法来实现这一点


我不想使用Rails的多态关联,因为我想保证数据库中的数据完整性。我知道我还需要定制Rails模型,但我们先不谈这个话题。主要的问题是如何编写一个迁移,使PK也成为FK(反之亦然)。

外键关系仅适用于最新版本的rails,如中所示,它是4.2,您可以这样使用它

创建简单外键

add_foreign_key :articles, :authors
生成:

ALTER TABLE "articles" ADD CONSTRAINT articles_author_id_fk FOREIGN KEY ("author_id") REFERENCES "authors" ("id")
您还应该知道,add_foreign_键只会生成一个外键约束,而不像activerecord add_列那样生成一个列

add_column :articles, :author_id, :integer
将产生:

ALTER TABLE "articles" ADD COLUMN author_id INT(11);
你可以找到更多信息

另外,如果你不只是在寻找rails的边缘,那么你会发现这个gem非常有用,它可以让你做你正在寻找的事情,你唯一需要注意的是,你必须使用与rails版本兼容的版本


我希望这会有所帮助:D

解决方案是在模型中手动设置主键和外键,而不是在迁移中摆弄(注意,您必须告诉Rails不要通过在选项中传递“id:false”来创建默认列id):

迁移:

def change
  create_table :VipPerson, id: false do |t|
    t.primary_key :person_id  # Normal integer PK, shouldn't auto-increment
    t.integer :vip_status
    ..... etc.
  end
end
在模型中:

class VipPerson < ActiveRecord::Base
  self.primary_key = "person_id"
  belongs_to :person, foreign_key: "person_id"
end
classvipperson

只需手动指向模型中的同一列。在数据库层,您还可以使用真正的外键约束(请参见Demi Magus答案)来增强主键。

实际上,这确实非常有用,谢谢。我也会用这个!但也许我应该更具体一点。从Rails的角度来看,我希望列是外键和主键。也就是说,我希望像t.primary_key和t.references这样的东西映射到同一列。我在我的原始问题中添加了伪代码。如果您在文档中没有找到它,那么很可能您找不到任何方法。另外,Rails的上一个版本大约在一个月前发布,因此它非常新,很难找到相关专家。如果你觉得我的答案有用,我将感谢你的支持:D.祝你好运;如果我的说法可能误导了你,我很抱歉。我的问题实际上并不局限于最新版本的Rails。事实上,自ActiveRecord开始以来,该问题就一直适用。像这样的数据库构造是一种常见的情况,在Rails出现之前就已经存在了。我真的不相信真的没有解决方案,因为像这样的场景很常见。另外,我的代表仍然太低,无法投票。别担心。嗯,在这种情况下,我听说这方面有很多优点,也许这一点对你会有帮助。实际上,如果你还想保证引用的完整性,你的答案是我答案的完美补充。:)