has_many或join - 使用我的桌子的'轨道方式'是什么?

时间:2014-01-31 15:26:08

标签: activerecord ruby-on-rails-4

我有一个跟踪事故的数据库。每次事故都有多种原因。每个原因在第3个表中都有一个友好的名称。什么是' rails方式'创建这种关联?

以下是我所拥有的:

create_table "accidents", force: true do |t|
  t.text     "notes"
  t.datetime "created_at"
  t.datetime "updated_at"
end

create_table "causes", force: true do |t|
  t.integer  "accident_id"
  t.integer  "cause_name_id"
  t.datetime "created_at"
  t.datetime "updated_at"
end

create_table "cause_names", force: true do |t|
  t.string   "name"
  t.datetime "created_at"
  t.datetime "updated_at"
end
CauseName.create :name => "DUI"
CauseName.create :name => "Speeding"

事故:

class Accident ActiveRecord::Base
  has_many :causes
end

原因:

class Cause < ActiveRecord::Base
  belongs_to :accidents
  has_one :cause_name
end

导致姓名:

class CauseName < ActiveRecord::Base
  belongs_to :causes
end

似乎是正确的&#34; ORM&#34; d,我这样使用它:

Accident.causes.first.cause_name.name #speeding
a = CauseName.find(1)
Accident.causes.first.cause_name = a #set and saved successfully

我一直在尝试各种各样的事情,但我似乎无法以我期望的方式工作。我知道我没有正确使用它。

我对rails和activerecord非常陌生,而且数据库很糟糕......我正在使用的架构是由我们的dba设计的,他们将在桌子上进行报告,但对Ruby一无所知或ActiveRecord。

在我的情况下,最好的方法是什么?我甚至使用这个东西吗?

2 个答案:

答案 0 :(得分:1)

在你的情况下,我建议不要将原因分成两个表。只需将name填入原因表并将其称为一天。

然后您可以轻松查询@accident.causes.first.name

答案 1 :(得分:1)

我认为您在belongs_to关联中错误地放置了has_oneCause - CauseName方法。

引用official guide

  

如果要在两个模型之间建立一对一的关系,   你需要将belongs_to添加到一个,并将has_one添加到另一个。怎么做   你知道哪个是哪个?

     

区别在于您放置外键的位置(它继续使用   声明属于all_to关联的类的表格,但是你   应该考虑一下数据的实际含义。   has_one关系说某事是你的 - 那   是的,有些东西指向你。

所以,在你的情况下,它应该是这样的:

class CauseName < ActiveRecord::Base
  has_one :cause # Note that I have changed :causes to singular too
end

class Cause < ActiveRecord::Base
  belongs_to :accident # <- Singularized too
  belongs_to :cause_name
end