Rails自我引用has_many关联

时间:2018-01-26 06:45:50

标签: ruby-on-rails associations has-many self-reference

使用Ruby on Rails,我认为我需要创建一个自引用的has_many关联来模拟中文单词。

背景:

每个单词都是多个组件单词的复合

例如,如果我有三个单词,' ni',' hao'和' nihao',我希望能够这样做:

nihao.components = ['ni', 'hao']

'ni'.composites = ['nihao']
'hao'.composites =['nihao']

我不相信这应该是一个等级关联(我已经看过几个宝石......),因为一个词没有1或2"父母",它有0,1或数百个"复合材料"。同样,一个单词有0,1或几个"组件"。

我试过了:

class Word < ActiveRecord::Base
  has_many :relationships
  has_many :components, through: :relationships, foreign_key: :component_id
  has_many :composites, through: :relationships, foreign_key: :composite_id
end

class Relationship < ActiveRecord::Base
  belongs_to :component, class_name: "Word"
  belongs_to :composite, class_name: "Word"
end

这不完全正确,因为我无法添加组件:

nihao.components << ni
   (0.2ms)  BEGIN
   (0.2ms)  ROLLBACK
ActiveModel::UnknownAttributeError: unknown attribute 'word_id' for Relationship.
        from (irb):5

数据库架构:

create_table "relationships", force: :cascade do |t|
    t.integer "component_id"
    t.integer "composite_id"
    t.datetime "created_at", null: false
    t.datetime "updated_at", null: false
  end

  create_table "words", force: :cascade do |t|
    t.string "characters"
    t.string "pinyin"
    t.string "opinyin"
    t.string "tpinyin"
    t.string "english"
    t.datetime "created_at", null: false
    t.datetime "updated_at", null: false
  end

1 个答案:

答案 0 :(得分:1)

试试这个,你没有正确地将你的模型与这种用例联系起来。

class Word < ActiveRecord::Base
  has_many :component_relationships, class_name: 'Relationship', foreign_key: :composite_id
  has_many :composite_relationships, class_name: 'Relationship', foreign_key: :component_id

  has_many :components, through: :component_relationships
  has_many :composites, through: :composite_relationships
end 

class Relationship < ActiveRecord::Base
  belongs_to :component, class_name: "Word", foreign_key: :component_id
  belongs_to :composite, class_name: "Word", foreign_key: :composite_id
end

我没试过这个,但这应该有效。