2017-10-14 28 views
0

A transaction_record有許多workflows,並且每個workflow有許多milestones。其中一個milestones的標記current: true,我想從transaction_recordcurrent_milestone去:Rails has_one:通過不同的型號名稱

class TransactionRecord < ApplicationRecord 
    has_many :workflows 
    has_many :milestones, through: :workflows 

    # DOES NOT WORK, but what I want to do... 
    has_one :current_milestone, through: :workflows, class: Milestone, source: :milestones 

    # Works, but want to make an association for including 
    def current_milestone 
    milestones.where(current: true).first 
    end 
end 

class Workflow < ApplicationRecord 
    belongs_to :transaction_record 
    has_many :milestones 
end 

class Milestone < ApplicationRecord 
    belongs_to :workflow 
end 

我可以創建一個返回所需milestone的方法,但我想讓它實際的關聯,所以我可以包括它的數據庫性能。

我有一個transaction_records#index頁面,其中我列出了每一個transaction_recordscurrent_milestone。這是一個n+1,除非我能弄清楚。

我真的希望能夠做類似:

@transaction_records = TransactionRecord.includes(:current_milestone) 

<% @transaction_records.each do |transaction_record| %> 
    <%= transaction_record.name %> - <%= transaction_record.current_milestone.name %> 
<% end %> 

更新

我可以指定transaction_recordmilestone間的方向關係,然後做transaction_record has_one :current_milestone, -> { where(current: true) }, class_name: Milestone。但現在我正在更改我的數據庫模式以獲得更高效的負載查詢。不是世界末日,但如果我已經有一個聯想,那不是我的偏好。

回答

0

說實話我不喜歡這個概念,transaction_record有一些active_milestone,沒有提及加入current_workflow

好的解決辦法是想想都workflowmilestone到必須current然後的能力:

class TransactionRecord < ApplicationRecord 
    has_one :current_workflow, .... 
    has_one :current_milestone, through: current_workflow, .... 
end 

class Workflow < ApplicationRecord 
    has_one :current_milestone, condition: .... 
end 

這遠不如我,但你仍然需要在workflow添加額外current標誌屬性。

這就是爲什麼更好的解決方案是重新修復你的概念。 從里程碑中刪除current並將current_milestone_id添加到工作流程。如果它是零,那麼這workflow沒有current_milestone。如果它包含一些ID,那麼這是您的current_workflowcurrent_milestone_id

代碼看起來很相似,但它不會有難看的情況Workflow