0

現在の役割に関連する特定の役割を見つけるために、確かに醜いクエリを実行する必要があります。この行は正しい結果を生成します。

@person_event_role.event_role.event.event_roles.
  joins(:mission_role).where(:mission_roles => {:title => 'Boss'}).
  first.person_event_roles.first.person

(複数の呼び出しから関連付けを推測できます)

この情報を取得する唯一の方法は、データベースの構造に関する大量の知識を必要としますが、結合を取り除くには...必要な情報を返すために、そのチェーンの各ステップで一連のヘルパー関数を入力する必要があります。 ..

4

1 に答える 1

1

ここですべきことは、必要に応じてヘルパー関数を作成することだと思います。あなたの関連チェーンの始まりがここにあるのかはわかりませんが、おそらく#eventを返すメソッドを割り当てますevent_role.event。そこから、event#boss_role、または意味的に意味のあるものを持ち、そのメソッドは

event_roles.joins(:mission_role).where(:mission_roles => {:title => 'Boss'}).first 

最後に、Eventモデルにも#bossメソッドがあります。

boss_roles.first.person_event_roles.first.person

したがって、元のクエリは次のようになります

@person_event_role.event.boss

チェーンの各脚は自己完結型で理解しやすく、チェーンの開始点が終了点について全知である必要はありません。これらの関連付けの完全な範囲を完全に理解しているわけではありませんが、それを 3 つまたは 4 つのモデル メソッドに分割するだけで、探している懸念事項を明確に読み取って分離できると確信しています。さらに読みやすくするために、さらに細分化することもできますが、それはスタイルの問題になります。

それが役立つことを願っています!

以下、元の質問者による

私はこのアドバイスに従って、最終的に次のようになったと思います。

@person_event_role.get_related_event_roles_for('Boss').first.filled_by.first

#person_event_role:
def get_related_event_roles_for(role)
  event.event_roles_for(role)
end

def event
 event_role.event
end

#event:
def event_roles_for(role)
  event_roles.for_role(role)
end

#event_role:
scope :for_role, lambda {|role| joins(:mission_role).where(:mission_roles => {:title => role})}
def filled_by
  person_event_roles.collect {|per| per.person}
end
于 2012-01-21T02:53:01.617 に答える