Techioz Blog

すでにフェッチされたモデルにリレーションをプリロードします

概要

私には、organization、base_url、ldap_group_permission という 3 つのモデルがあります。 Organization は、base_url と 1 対多の関係を持ち、ldap_group_permission とも同じ関係を持ちます。 current_organization という名前の組織モデルのフェッチされたレコードを保持する変数がすでに存在します。

もちろん、 current_organization.base_urls を実行して、組織のbase_urlsを取得できます。しかし、問題は、base_url ごとに ldap_group_permission も必要な点にあります。各base_urlを介してループを実行することもできますが、N+1クエリの問題が発生し、各base_urlがデータベース内で個別のクエリを実行することになり、パフォーマンスが低下します。

1 つのクエリで ldap_group_permissions も取得しながら、current_organization のbase_urls を取得するにはどうすればよいですか?

解決策

このように関連付けられたレコードを積極的にロードして current_organization を定義できます

current_organization = Organization.includes(base_urls: :ldap_group_permissions).find(id)

そして列挙してみると

current_organization.base_urls.each do |base_url|
  base_url.ldap_group_permissions.each do |ldap_group_permission|
    # Access every ldap_group_permission
  end
end

こうすればN+1を回避できます