我有两张桌子:
货币和汇率
currencies: id:int, code:string, name: string
rates: id:int, top_currency_id:int, bottom_currency_id:int, rate:float
我有两个活跃的记录:
class Rate < ActiveRecord::Base
attr_accessible :bottom_currency, :rate, :top_currency, :top_currency_id
belongs_to :top_currency, :class_name => 'Currency', :foreign_key => 'top_currency_id'
belongs_to :bottom_currency, :class_name => 'Currency', :foreign_key => 'bottom_currency_id'
end
class Currency < ActiveRecord::Base
attr_accessible :code, :name
has_many :rates
end
所以问题是: 当我想执行以下代码时: top_currency = Currency.find_by_id(1) @test = Rate.where(:top_currency =&gt; top_currency)
我收到以下错误:
Mysql2::Error: Unknown column 'rates.top_currency' in
'where clause': SELECT `rates`.* FROM `rates` WHERE `rates`.`top_currency` = 1
为什么Rails的魔法不起作用?
非常感谢。
答案 0 :(得分:5)
在您的两个belongs_to
方法中,将foreign_key
选项更改为primary_key
,将其他所有内容保留为原样。
belongs_to :top_currency, :class_name => 'Currency', :primary_key => 'top_currency_id'
# ...
默认情况下,关联对象的主键为id
。但是,您的货币模型有三个主键,预期id
加上两个额外的键:top_currency_id
和bottom_currency_id
。 Active Record需要知道要查找的密钥。用primary_key
选项告诉它。
当外键与关联名称(foreign_key
)加“belongs_to :name
”不同时,需要_id
选项。由于您的外键与关联名称加“_id
”匹配,因此您无需使用foreign_key
选项。
答案 1 :(得分:3)
从我看来,你的代码应该在理论上运作。但我确实认为你有点多余。
这样就足够了:
class Rate < ActiveRecord::Base
belongs_to :top_currency, class_name: 'Currency'
belongs_to :bottom_currency, class_name: 'Currency'
end
Rails会推断top_currency
的外键为top_currency_id
,bottom_currency_id
为bottom_currency
。
答案 2 :(得分:0)
我不认为你可以查询这样的关系。要使用您的示例:
top_currency = Currency.find_by_id(1)
@test = Rate.where(:top_currency=>top_currency)
您必须将其更改为:
top_currency = Currency.find_by_id(1)
@test = Rate.where(:top_currency_id => top_currency.id)
但这样做可能更容易:
top_currency = Currency.find_by_id(1)
@test = top_currency.rates