関連付け
項目一覧
Overview
Mongoid の関連付けにより、モデル間の関係を作成できます。 このガイドでは、Mongoid がサポートするさまざまなタイプの関連付けと、アプリケーションでそれらを使用する方法について学習できます。
参照された関連付け
参照された関連付けを使用すると、2 つのモデル間の関係を作成し、一方のモデルが他方のモデルを参照できます。 Mongoid は、次の参照される関連付けのタイプをサポートしています。
has_one
has_many
belongs_to
has_and_belongs_to_many
次のセクションでは、これらのそれぞれの関連付けタイプの使用方法について説明します。
が 1 つ
has_one
マイクロを使用して、1 つのクラスで表されるドキュメントに、別の 子クラスによって表されるドキュメントも含まれていることを宣言できます。 次の例では、 Studio
クラスに対する has_one
の関係を持つ Band
クラスを作成します。
class Band include Mongoid::Document has_one :studio end
has_one
関連付けを宣言する場合、子クラスは親クラスを参照する belongs_to
関連付けも使用する必要があります。 次の例では、先行する Band
クラスで参照されている Studio
クラスを示しています。
class Studio include Mongoid::Document belongs_to :band end
belongs_to
マイクロの詳細については、「 が に属する 」セクションを参照してください。
次の例に示すように、検証を使用して、子クラスが親クラスに存在することを確認できます。
class Band include Mongoid::Document has_one :studio validates_presence_of :studio end
が多い
has_many
マイクロを使用して、クラスによって表されるドキュメントに、別のクラスによって表される複数の子ドキュメントが含まれていることを宣言できます。 次の例では、 Members
クラスに対する has_many
の関係を持つ Band
クラスを作成します。
class Band include Mongoid::Document has_many :members end
has_many
関連付けを宣言する場合、子クラスは親クラスを参照する belongs_to
関連付けも使用する必要があります。 次の例では、先行する Band
クラスで参照されている Member
クラスを示しています。
class Member include Mongoid::Document belongs_to :band end
マイクロの詳細については、 [ Belongs To ]belongs_to
セクションを参照してください。
次の例に示すように、検証を使用して、子クラスが親クラスに存在することを確認できます。
class Band include Mongoid::Document has_many :members validates_presence_of :members end
Mongoid の検証の詳細については、「 検証ガイド 」を参照してください。
関連付け情報の検索
has_many
関連付けで any?
メソッドを使用すると、データベースからドキュメントセット全体を取得せずに、関連付けにドキュメントが含まれているかどうかを判断できます。
次の例では、 any?
メソッドを使用して、Band
クラスのドキュメントに Members
ドキュメントが含まれているかどうかを判断します。
band = Band.first band.members.any?
次の例に示すように、any?
メソッドをフィルターと併用して、指定された条件に一致するドキュメントを検索することもできます。
band = Band.first band.members.any? { |member| member.instrument == 'piano' }
any?
メソッドにクラス名を指定すると、クラスの名前で結果をフィルタリングできます。 これは多態的な 関連付けに便利です。
class Drummer < Member end band = Band.first band.members.any?(Drummer)
注意
関連付けられているクラスのデータが Mongoid に読み込まれた後は、any?
メソッドに対する後続の呼び出しでは、データベースはクエリされません。 代わりに、Mongoid はメモリにすでにロードされているデータを使用します。
また、exists?
メソッドを呼び出して、関連付け内に永続化されたドキュメントがあるかどうかを確認することもできます。 exists?
メソッドは常にデータベースをクエリし、データベースに保存されているドキュメントのみをチェックします。 exists?
メソッドはフィルタリングを許可しておらず、引数を受け入れません。
次の例では、 exists?
メソッドを使用して、Band
クラスに永続化された Members
ドキュメントがあるかどうかを判断します。
band = Band.create! # Member is not persisted. band.members.build band.members.exists? # Outputs: false # Persist the member band.members.map(&:save!) band.members.exists? # Outputs: true
に属します
belongs_to
マイクロを使用して、1 つのクラスによって表されるドキュメントが、別のクラスによって表されるドキュメントの子であることを宣言します。 デフォルトでは 、親クラスの _id
フィールドは子クラスに保存されます。 次の例では、 Band
クラスへの belongs_to
の関連付けを持つ Members
クラスを作成します。
class Members include Mongoid::Document belongs_to :band end
次の例に示すように、optional
オプションを true
に設定することで、Mongoid が関連付けられている親クラスの _id
を保存せずにドキュメントをデータベースに永続化できるようにします。
class Members include Mongoid::Document belongs_to :band, optional: true end
Tip
アプリケーションの 構成設定 で belongs_to_required_by_default
構成オプションを false
に設定することで、belongs_to
関連付けのデフォルトの動作をグローバルに変更して、親クラスを不要にすることができます。
親クラスで一致する has_one
または has_many
の関連付けを指定しなくても、子クラスで belongs_to
の関連付けを指定できます。 そうすると、親クラスから子ドキュメントのフィールドにはアクセスできませんが、親の _id
フィールドなど、子クラスに保存されている親フィールドにはアクセスできます。 次の例では、Band
クラスはMembers
クラスにアクセスできませんが、Members
クラスはBand
クラス にアクセスできます。
class Band include Mongoid::Document end class Members include Mongoid::Document belongs_to :band end
明確にするために、次の例に示すように、親クラスに子クラスへの has_one
または has_many
の関連付けが含まれていないことを示す、inverse_of
オプションを nil
に設定できます。
class Band include Mongoid::Document end class Members include Mongoid::Document belongs_to :band, inverse_of: nil end
を持つ と が多数に属する
has_and_belongs_to_many
マイクロを使用して、クラスモデルに別のクラスとの多対多の関係が含まれていることを宣言します。 多対多の関係では、1 つのクラス内の各ドキュメントを別のクラスの複数のドキュメントに関連付けることができます 。 次の例では、 Members
クラスへの has_and_belongs_to_many
の関係を持つ Band
クラスを作成します。 Band
ドキュメントは複数の Members
ドキュメントを参照でき、Members
ドキュメントは複数の Band
ドキュメントを参照できます。
class Band include Mongoid::Document has_and_belongs_to_many :members end class Members include Mongoid::Document has_and_belongs_to_many :bands end
has_and_belongs_to_many
の関連付けを宣言すると、両方のモデル インスタンスに関連付けられているドキュメントの _id
値のリストが保存されます。 関連するドキュメントの _id
値をモデル インスタンスの 1 つだけに保存するには、inverse_of
オプションを nil
に設定します。 次の例では、関連付けられているドキュメントの _id
値を Band
クラスのみに保存するように Mongoid に指示します。
class Band include Mongoid::Document has_and_belongs_to_many :tags, inverse_of: nil end class Tag include Mongoid::Document end
Tip
has_and_belongs_to_many
の関連付けがあるドキュメントを更新すると、Mongoid は更新されたドキュメントの updated_at
フィールドを設定しますが、関連付けられているドキュメントの updated_at
フィールドは設定しません。
クエリ参照の関連付け
集計パイプラインを使用して、参照されている関連付け全体のドキュメントをクエリできます。 集計パイプラインと、複数のコレクションにわたるクエリを作成したり、指定した形式でデータを操作したりできます。 集計パイプライン の使用方法の詳細については、 集計ガイドを参照してください。
単純なクエリの場合は、関連付けを直接クエリできます。 コレクションを直接クエリする場合、コレクション自体にあるフィールドと値のみをクエリできます。 クエリ対象に関連付けられているコレクションを直接クエリすることはできません。
例、次の Band
クラスと Tour
クラスについて考えてみます。
class Band include Mongoid::Document has_many :tours field :name, type: String end class Tour include Mongoid::Document belongs_to :band field :year, type: Integer end
次の例では、 year
の値が 2000
以上であるドキュメントを Tour
クラスでクエリし、それらのドキュメントの band_id
を保存します。 次に、それらの band_id
値を持つドキュメントを Band
クラスでクエリします。
band_ids = Tour.where(year: {'$gte' => 2000}).pluck(:band_id) bands = Band.find(band_ids)
埋め込み関連付け
埋め込み関連付けを使用して、異なるタイプのドキュメントを同じコレクションに保存できます。 Mongoid は次のマイクロとの埋め込み関連付けをサポートしています。
embeds_one
embeds_many
embedded_in
recursively_embeds_one
recursively_embeds_many
次のセクションでは、これらの関連付けタイプの使用方法について説明します。
埋め込み 1
クラスモデルに別のクラスタイプの埋め込みドキュメントが含まれていることを指定するには、親クラスの embeds_one
マイクロと 埋め込みクラスの embedded_in
マイクロを使用します。 次の例では、埋め込まれた Label
クラスを持つ Band
クラスを作成しています。
class Band include Mongoid::Document embeds_one :label end class Label include Mongoid::Document field :name, type: String embedded_in :band end
Mongoid は、親ドキュメントの embeds_one
マイクロで埋め込まれたドキュメントを、埋め込みクラスと同じ名前のフィールドとして保存します。 前述の Label
ドキュメントは、次の例に示すように、 Band
ドキュメントに保存されています。
# Band document { "_id" : ObjectId("..."), "label" : { "_id" : ObjectId("..."), "name" : "Periphery", } }
次の例に示すように、store_as
オプションを使用して、埋め込みドキュメントを別の名前で保存することができます。
class Band include Mongoid::Document embeds_one :label, store_as: "record_label" end
埋め込みが多い
クラスモデルに異なるクラスタイプの複数の埋め込みドキュメントが含まれていることを指定するには、親クラスの embeds_many
構造と 埋め込みクラスの embedded_in
マイクロを使用します。 次の例では、複数の埋め込まれた Album
型ドキュメントを含む Band
クラスを作成しています。
class Band include Mongoid::Document embeds_many :albums end class Album include Mongoid::Document field :name, type: String embedded_in :band end
Mongoid は、親ドキュメントに embeds_many
マイクロで埋め込まれたドキュメントを、埋め込みクラスと同じ名前の配列フィールドとして保存します。 前述の Album
ドキュメントは、次の例に示すように、 Band
ドキュメントに保存されています。
{ "_id" : ObjectId("..."), "albums" : [ { "_id" : ObjectId("..."), "name" : "Omega", } ] }
次の例に示すように、store_as
オプションを使用して、埋め込みドキュメントを別の名前で保存することができます。
class Band include Mongoid::Document embeds_many :albums, store_as: "records" end
再帰埋め込み
recursively_embeds_one
と recursively_embeds_many
マイクロを使用して、同じタイプの 1 つ以上のドキュメントを親クラスに埋め込むことができます。 どちらのドキュメントも、parent_*
メソッドと child_*
メソッドを介して親ドキュメントと子ドキュメントにアクセスできます。ここで、*
はクラスの名前を表します 。 次の例では、複数のバンド名を表すために他の複数の Band
ドキュメントを再帰的に埋め込む Band
クラスを作成します。
class Band include Mongoid::Document field :name, type: String recursively_embeds_many end
次の例に示すように、parent_band
メソッドと child_band
メソッドを介して親ドキュメントと子ドキュメントにアクセスできます。
root = Band.new(name: "Linkin Park") # Add child bands child_one = root.child_band.build(name: "Lincoln Park") child_two = root.child_band.build(name: "Xero") # Access parent band child_one.parent_band # Outputs: root
埋め込み関連付けのクエリ
ドット表記を使用して親クラスのコレクションをクエリするときに、埋め込みドキュメントにアクセスできます。
次の例では、ドット表記を使用して、Band
クラスに埋め込まれている Tour
型のドキュメントをクエリします。 クエリでは、tours.year
の値が 2000
以上であるドキュメントが返されます。
Band.where('tours.year' => {'$gte' => 2000})
次の例に示すように、pluck
プロジェクションメソッドを使用すると、関連付けられている親ドキュメントを取得せずに埋め込みドキュメントを取得できます。
# Get awards for bands that have toured since 2000 Band.where('tours.year' => {'$gte' => 2000}).pluck(:awards)
Mongoid クエリ メソッドを使用して 埋め込み一致 を実行できます。これにより、アプリケーションにすでにロードされているドキュメントの埋め込み関連付けに対してクエリを実行できます。Mongoid は、サーバーにクエリを送信せずに埋め込み一致を実装します。
次のクエリ演算子は埋め込み一致でサポートされています。
次の例では、 $gte
比較演算子を使用して、ロードされた Band
ドキュメントの埋め込み tours
フィールドをクエリします。
band = Band.where(name: 'Astral Projection').first tours = band.tours.where(year: {'$gte' => 2000})
ロードされたドキュメントでの埋め込み一致には、次の既知の制限があります。
次の機能では、埋め込み一致は実装されていません。
JavaScriptコードを実行する演算子( $where など)
$expr や $jsonSchema などの他のサーバー機能に実装される演算子
Mongoid は、
$gte
と$lte
条件を使用して、Range
引数をハッシュに展開します。 これにより、場合によっては無効なクエリが発生し、InvalidQuery
例外が発生します。$regex
演算子では、$options
フィールドにオプションも提供しながら、正規式オブジェクトをパターンとして指定することはできません。 正規式パターンが string の場合にのみオプションを指定できます。MongoDB Serverバージョン 4.0 以前では、
$type
引数は厳密に検証されません。
_id フィールドの省略
デフォルトでは 、Mongoid は埋め込みドキュメントに _id
フィールドを追加します。 このフィールドは、モデルで _id
フィールドを明示的に指定し、デフォルト値を省略することで、埋め込みドキュメントから省略できます。 次の例ではMongoid に Albums
クラスに _id
フィールドを追加しないように指示します。
class Album include Mongoid::Document field :name, type: String field :_id, type: Object embedded_in :band end
前述の Albums
クラスでは、_id
フィールドは自動的に追加されません。 デフォルト値がない場合、モデルでデフォルト値を指定しない限り、Mongoid はデータベースに値を保存しません。
埋め込み関連付けの削除
次のいずれかの方法を使用して、embeds_many
の関連付けから子ドキュメントを削除できます。
clear
delete_all
destroy_all
clear
メソッドは $unset 演算子を使用して、親ドキュメントから埋め込み関連付け全体を削除します。clear
メソッドは destroy
コールバックを実行しません。 次の例では、 clear
メソッドを使用して、Band
クラスからすべての埋め込み関連付けを削除します。
band = Band.find(...) band.tours.clear
delete_all
メソッドは $pullAll 演算子を使用して、埋め込み関連付け内のドキュメントを削除します。delete_all
は、関連付けがまだ読み込まれていない場合はその関連付けを読み込み、アプリケーションに存在するドキュメントのみを削除します。 delete_all
メソッドは destroy
コールバックを実行しません。 次の例では、 delete_all
メソッドを使用して、Band
クラスからすべての埋め込み Album
ドキュメントを削除します。
band = Band.find(...) band.tours.delete_all
destroy_all
メソッドでは、埋め込み関連付け内のドキュメントを削除するために、 $pullAll 演算子も使用されます。また、関連するドキュメントに定義されている destroy
コールバックも実行します。 次の例では、 destroy_all
メソッドを使用して、Band
クラスからすべての埋め込み Album
ドキュメントを削除します。
band = Band.find(...) band.tours.destroy_all
関連付けの動作をカスタマイズする
Mongoid を使用して、アプリケーション内で関連付けがどのように動作するかをカスタマイズできます。 次のセクションでは、関連付けの動作をカスタマイズする方法について説明します。
拡張機能
拡張機能を使用すると、関連付けにカスタム機能を追加できます。 次の例に示すように、関連付け定義で ブロックを指定することで、関連付けで拡張機能を定義できます。
class Band include Mongoid::Document embeds_many :albums do def find_by_name(name) where(name: name).first end end end band.albums.find_by_name("Omega") # returns album "Omega"
カスタム関連付け名
関連付けのカスタムクラス名を指定するには、class_name
コマンドを使用します。 これは、クラスの名前とは異なるものに関連付けに名前を付けたい場合に便利です。 次の例では、 class_name
マイクロを使用して、records
という埋め込み関連付けが Album
クラスを表すことを指定します。
class Band include Mongoid::Document embeds_many :records, class_name: "Album" end
カスタムキー
デフォルトでは 、Mongoid は関連付けを検索するときに親クラスの _id
フィールドを使用します。 primary_key
と foreign_key
マイクロを使用して、使用する別のフィールドを指定できます。 次の例ではBand
クラスの albums
関連付けの新しいプライマリキーと外部キーを指定します。
class Band include Mongoid::Document field :band_id, type: String has_many :albums, primary_key: 'band_id', foreign_key: 'band_id_ref' end class Album include Mongoid::Document field :band_id_ref, type: String belongs_to :band, primary_key: 'band_id', foreign_key: 'band_id_ref' end
has_and_belongs_to_many
の関連付けを指定している場合は、inverse_primary_key
と inverse_foreign_key
マイクロも使用できます。 inverse_primary_key
マニュアルは、リモート モデルがドキュメントを検索するために使用するローカル モデルのフィールドを指定します。 inverse_foreign_key
マイクロは、inverse_primary_key
で見つかった値を保存するリモート モデルのフィールドを指定します。
次の例では、 has_and_belongs_to_many
の関連付けにおいて Band
クラスと Members
クラスの新しいプライマリキーと外部キーを指定します。
class Band include Mongoid::Document field :band_id, type: String field :member_ids, type: Array has_many :members, primary_key: 'member_id', foreign_key: 'member_ids', inverse_primary_key: 'band_id', inverse_foreign_key: 'band_ids' end class Member include Mongoid::Document field :member_id, type: String field :band_ids, type: Array has_many :bands, primary_key: 'band_id', foreign_key: 'band_ids', inverse_primary_key: 'member_id', inverse_foreign_key: 'member_ids' end
カスタムスコープ
scope
パラメータを使用して、関連付けの範囲を指定できます。 scope
パラメーターは、Mongoid が関連付けの一部と見なすドキュメントを決定します。 スコープ指定された関連付けでは、クエリ時にスコープ条件に一致するドキュメントのみが返されます。 scope
は、アーティッドがゼロの Proc
または、関連付けられたモデル上の名前付きスコープを参照する Symbol
に設定できます。 次の例では、 Band
クラスでの関連付けにカスタム スコープを設定します。
class Band include Mongoid::Document has_many :albums, scope: -> { where(published: true) } # Uses a scope called "upcoming" on the Tour model has_many :tours, scope: :upcoming end
注意
スコープ条件に一致しないドキュメントを 関連付けに追加できます。 Mongoid はドキュメントをデータベースに保存し、関連するメモリに表示されます。 ただし、関連付けをクエリするときに、ドキュメントは表示されません。
検証
Mongoid が関連付けをメモリに読み込むとき(デフォルトでは )、validates_associated
マイクロを使用して子も存在することを検証します。 Mongoid は、次の関連付けタイプの子を検証します。
embeds_many
embeds_one
has_many
has_one
has_and_belongs_to_many
この検証動作をオフにするには、次の例に示すように、関連付けを定義するときに validate
マイクロを false
に設定します。
class Band include Mongoid::Document embeds_many :albums, validate: false end
多形
Mongoid は、子クラスの 1 対 1 および 1 対多の関連付けの多形データをサポートします。 多形関連付けにより、1 つの関連付けに異なるクラスタイプのオブジェクトを含めることができます。 子関連付けで polymorphic
オプションを true
に設定し、親関連付けに as
オプションを追加することで、多態的な 関連付けを定義できます。 次の例では、 Band
クラスで多態的な 関連付けを作成しています。
class Tour include Mongoid::Document has_one :band, as: :featured end class Label include Mongoid::Document has_one :band, as: :featured end class Band include Mongoid::Document belongs_to :featured, polymorphic: true end
前の例では、Band
クラスの :featured
の関連付けに Label
または Album
のドキュメントのいずれかを含めることができます。
重要
Mongoid は、子から親への多形データのみをサポートします。 親の has_one
または has_many
の関連付けを多形として指定することはできません。
has_and_belongs_to_many
関連付けは多形データをサポートしていません。
カスタム多形タイプ
バージョン 9.0.2 以降、 Mongoid は、グローバル レジストリを通じてカスタム多形型をサポートします。 別のキーを指定して異なるクラスを表すことができ、コードを データから切り離します。 次の例ではBand
クラスの代替キーとして string "artist"
を指定します。
class Band include Mongoid::Document identify_as 'artist' has_many :albums, as: :record end
前の例では、identify_as
ディレクティブは Mongoid に指示して、データベースにBand
クラスをstring"artist"
として保存します。
次の例に示すように、複数のエイリアスを指定することもできます。
class Band include Mongoid::Document identify_as 'artist', 'group', 'troupe' has_many :albums, as: :record end
前の例では、artist
はデフォルト名で、その他はレコードを検索する目的でのみ使用されています。 これにより、データの 関連付けを中断せずにコードをリファクタリングできます。
多形型エイリアスはグローバルです。 指定するキーは、コード ベース全体で一意である必要があります。 ただし、モデルのさまざまなサブセットに使用できる代替のリゾルバを登録することはできます。 この場合、キーは各リゾルバに対してのみ一意である必要があります。 次の例は、代替リゾルバを登録する方法を示しています。
Mongoid::ModelResolver.register_resolver Mongoid::ModelResolver.new, :mus Mongoid::ModelResolver.register_resolver Mongoid::ModelResolver.new, :tool module Music class Band include Mongoid::Document identify_as 'bnd', resolver: :mus end end module Tools class Band include Mongoid::Document identify_as 'bnd', resolver: :tool end end
Music::Band
と Tools::Band
は両方とも "bnd"
のエイリアスですが、各モデルは競合を回避するために独自のリゾルバを使用します。
依存関係の動作
参照された関連付けに dependent
オプションを指定すると、ドキュメントが削除されたときに Mongoid が関連するドキュメントをどのように取り扱うかを指定できます。 次のオプションを指定できます。
delete_all
: モデル コールバックを実行中せずにすべての子ドキュメントを削除します。destroy
: 子ドキュメントを削除し、すべてのモデル コールバックを実行します。nullify
: 子ドキュメントの外部キーをnil
に設定します。 親ドキュメントのみが参照する場合、子ドキュメントが 孤立する 可能性があります。restrict_with_exception
: 子ドキュメントが空でない場合に例外が発生します。restrict_with_error
: 子ドキュメントが空でない場合は、操作をキャンセルし、false
を返します。
dependent
オプションを指定しない場合、親ドキュメントが削除されても Mongoid は子ドキュメントを変更せずに残ります。 子ドキュメントは削除された親ドキュメントを参照、親のみを介して参照されると、子ドキュメントは孤立します。
次の例ではBand
クラスで dependent
オプションを指定します。
class Band include Mongoid::Document has_many :albums, dependent: :delete_all belongs_to :label, dependent: :nullify end
参照された関連付けの自動保存
デフォルトでは 、Mongoid は親ドキュメント を保存するときに、非埋め込み関連付けから関連するドキュメントを自動的に保存しません。 これにより、存在しないドキュメントへの参照が切断される可能性があります。
参照された関連付けで autosave
オプションを使用すると、親ドキュメント を保存するときに関連するドキュメントを自動的に保存できます。 次の例では、関連付けられた Album
クラスを持つ Band
クラスを作成し、autosave
オプションを指定しています。
class Band include Mongoid::Document has_many :albums end class Album include Mongoid::Document belongs_to :band, autosave: true end band = Band.new album = Album.create!(band: band) # The band is persisted at this point.
注意
Mongoid は、accepts_nested_attributes_for
オプションを使用する関連付けにオート保存機能を自動的に追加します。
Mongoid は親ドキュメントに埋め込みドキュメントを保存するため、埋め込み関連付けに autosave
オプションを指定する必要はありません。
自動構築
has_one
や embeds_one
などの 1 対 1 の関連付けに autobuild
オプションを追加すると、nil
関連付けにアクセスするときに新しいドキュメントを自動的にインスタンス化できます。 次の例では、 Band
クラスの関連付けに autobuild
オプションを追加します。
class Band include Mongoid::Document embeds_one :label, autobuild: true has_one :producer, autobuild: true end
タップ
Mongoid がドキュメントに入力すると、ドキュメントのupdated_at
フィールドが現在の日付と時刻に更新されます。任意の belongs_to
関連付けに touch
オプションを追加すると、子ドキュメントが更新されるたびに Mongoid が親ドキュメントにアクセスするようになります。 次の例では、 Band
クラスの関連付けに touch
オプションを追加します。
class Band include Mongoid::Document field :name belongs_to :label, touch: true end
touch
オプションを使用して、親関連付けの別のフィールドをstring またはシンボルとして指定することもできます。 Mongoid が親関連付けにアクセスすると、updated_at
フィールドと指定されたフィールドの両方が現在の日付と時刻に設定されます。
次の例ではMongoid に bands_updated_at
フィールドにアクセスするように指示します。
class Band include Mongoid::Document belongs_to :label, touch: :bands_updated_at end
注意
埋め込み関連付けでは、埋め込みドキュメントが操作されると、Mongoid はその親を再帰的に操作します。 このため、embedded_in
の関連付けに touch
属性を追加することは不要です。
Mongoid は、embedded_in
関連付けでアクセスする追加フィールドの指定をサポートしていません。
カウンター キャッシュ
関連付けられたフィールドに属するオブジェクトの数を保存するには、counter_cache
オプションを使用します。 このオプションを指定すると、Mongoid はカウントを保存するために関連付けられたモデルに追加の属性を保存します。 このため、関連付けられているクラスで Mongoid::Attributes::Dynamic
モジュールを指定する必要があります。
次の例ではBand
クラスに counter_cache
オプションを追加し、 Label
クラスで Mongoid::Attributes::Dynamic
を指定します。
class Band include Mongoid::Document belongs_to :label, counter_cache: true end class Label include Mongoid::Document include Mongoid::Attributes::Dynamic has_many :bands end
関連付けメタデータ
関連付けを定義すると、Mongoid はその関連付けに関するメタデータを保存します。 メタデータにアクセスするには、モデルクラスまたはドキュメントで reflect_on_association
メソッドを呼び出すか、特定のドキュメントのメタデータに直接アクセスします。 次の例は、 reflect_on_association
メソッドと直接アクセスによってメタデータにアクセスする方法を示しています。
# Get the metadata for a named association from the class or document Model.reflect_on_association(:<association_name>) # Directly access metadata on a document model.associations[:<association_name>]
注意
前の例の <association_name>
を関連付け名に置き換えます。
属性
すべての関連付けには、関連するドキュメントに関する情報を保存する属性が含まれています。 関連付けには、次の属性が含まれます。
_target
: プロキシされたドキュメント(1 つまたは複数)_base
: 関連付けが定義されているドキュメント_association
: 関連付けに関する情報
次の例では、前述の各属性にアクセスします。
class Band include Mongoid::Document embeds_many :songs end Band.songs = [ song ] Band.songs._target # returns [ song ] Band.songs._base # returns band Band.songs._association # returns the association metadata
次の表は、_association
属性に保存されている情報を示しています。
方式 | 説明 |
---|---|
| 多態的な子に対する親の名前。 |
|
|
| 関連付けが自動構築であるかどうかを返します。 |
| 関連付けが自動保存されているかどうかを返します。 |
| 関連付けに親から階層化されたコールバックがあるかどうかを返します。 |
| プロキシされたドキュメントのクラス名。 |
| 関連付けが定期的な関連付けであるかどうかを返します。 |
| 関連付けの依存関係オプション。 |
| 関連付けに依存している削除または破棄するメソッドがある場合は |
| 関連付けが別のドキュメントに埋め込まれているかどうかを返します。 |
| 関連付けに |
| 外部キーフィールドの名前。 |
| 外部キー フィールドのダーティ チェック メソッドの名前。 |
| 外部キー フィールドのセッターの名前。 |
| 外部キーが自動インデックス化されているかどうかを返します。 |
| すべての逆関連付けの名前。 |
| 単一の逆関連付けの名前。 |
| 逆側の関連付けのクラス名。 |
| 逆側の外部キーフィールドの名前。 |
| 逆側の関連付けのクラス。 |
| 逆側の関連付けのメタデータ。 |
| 逆関連付けの明示的に定義された名前。 |
| 逆を設定するために使用されるメソッドの名前。 |
| 逆の多形タイプフィールドの名前。 |
| 多形型フィールドの逆のセッターの名前。 |
| 関連付けを取得するために使用される、属性のハッシュ内のフィールドの名前。 |
| 関連付け内のプロキシされたドキュメントのクラス。 |
| 関連付け名。 |
| ActiveRecord とのAPI互換性のために |
| 関連付けのカスタム並べ替えオプション。 |
| 関連付けが多形であるかどうかを返します。 |
| 関連付けを設定するフィールドの名前。 |
| 埋め込み関連付けを保存する属性の名前。 |
| 関連付けにアクセス オプションがあるかどうかを返します。 |
| 多形型を取得するフィールドの名前。 |
| 多形タイプを設定するフィールドの名前。 |
| 関連付けに関連する検証があるかどうかを返します。 |