Rails - has_one与两个参数的关联

时间:2013-12-08 21:05:01

标签: sql ruby-on-rails rails-activerecord

我有一个名为assets的表,它有许多版本。版本有版本号。每个资产还有一个version_number列,表示最新(最新)版本。

我想在资产及其最新版本之间建立关联,但我找不到有关如何执行此操作的任何文档。从理论上讲,它看起来像这样

asset.rb

has_one :latest, class_name: "Version", foreign_key: ["asset_id", "version_number"], primary_key: ["id", "version_number"]

一种天真的方法是:

asset.rb

def latest
  Version.where(asset_id: asset.id, version_number: asset.version_number).first
end

在代码中执行此操作的问题是,我无法在资产的association_cache中加载“最新”。当我加载一组资产时,我也无法轻易地加载所有关联的“最新”记录,例如Asset.includes(:latest).where(project_id: 7)

我认为应该的原因是因为多态关联使用了两个参数。

1 个答案:

答案 0 :(得分:0)

我在输入问题后实际上发现了解决方案,这有助于我更好地表达问题。解决方案来自http://pivotallabs.com/rails-associations-with-multiple-foreign-keys/

TLDR;

has_one :latest, class_name: 'Version', foreign_key: :asset_id, primary_key: :id, conditions: Proc.new{|join_association|
  if join_association
    "versions.version_number = assets.version_number"
  else
    {version_number: version_number}
  end
}

我不得不稍微调整一下"versions.version_number = version_number"行,因为在一些急切加载的情况下,SQL会抱怨关键版本号码的含糊不清。所以,我添加assets.来消除这种歧义并解决问题。我会再次回应他们所说的话,即joins(:latest)时你必须​​includes(:latest)