MongoDB ビューは、コレクションまたは別のビューに対する読み取り専用のクエリ定義 です。ビューが保存するのは集約パイプラインであり、その結果ではないため、読み取り ごとに現在のソースデータへパイプラインが適用されます。したがって標準ビューは マテリアライズドビューのキャッシュを提供しません。
ビューを作成する #
db.createView() は対象コレクション名、ソース名前空間、集約パイプラインを受け取ります。
db.createView(
"active_orders",
"orders",
[
{ $match: { status: "active" } },
{ $project: { customerId: 1, total: 1, createdAt: 1 } }
]
)クライアントはコレクションと同じように active_orders をクエリします。
db.active_orders.find({ customerId: customerId })サーバーはビュー定義とクライアントクエリを組み合わせ、ソースコレクションに対して
結果を計画します。標準ビューは基盤となるコレクションのインデックスを使用します。
汎用インデックスを標準ビューへ直接作成、削除、再構築することはできません。選択性
の高い $match ステージを先頭に置き、パイプラインとクライアントクエリが使うソース
フィールドにインデックスを設定します。
Views can also be created with db.createCollection():
db.createCollection("recent_orders", {
viewOn: "orders",
pipeline: [
{ $match: { createdAt: { $gte: ISODate("2026-01-01") } } }
],
collation: { locale: "en", strength: 2 }
})ビューとそのソースは同じデータベースに存在しなければなりません。ビューのデフォルト 照合順序は作成時に固定され、クエリで別の照合順序に上書きすることはできません。
設計上の制約 #
ビューはフィールドの一部を公開したり、フィールド名を変更したり、$lookup で別の
コレクションを結合したり、データを集約したりできます。insert、update、delete は
受け付けません。$out や $merge などのデータを書き込むサポート対象外の集約
ステージは、標準ビュー定義に含められません。
ビューは別のビューに依存できますが、依存グラフに循環を含めてはなりません。パイプ
ラインは決定的かつ有界に保ちます。リクエストごとに大規模な $lookup、$group、
ソートを実行するパイプラインは、運用コストを書き込みから読み取りへ移します。
ビューは時点読み取りやスナップショット読み取り分離をサポートしません。ブロッキング 集約ステージは、サーバーの集約メモリと一時ファイルの動作にも従います。パイプライン をビューの背後に隠せば安価になると仮定せず、最終クエリを explain して負荷テストします。
認可とスキーマの境界 #
認証が有効な場合、ビュー作成にはデータベースの createCollection 権限と参照する
名前空間への関連する読み取り権限が必要です。ビューのクエリにはビュー名前空間への
find 権限が必要ですが、クライアントはソースコレクションへの直接の find 権限を
別途必要としません。
認可の分離により、個人識別情報フィールドを含まない従業員レコードなど、制御された 射影を公開できます。他の権限でソースコレクション、メタデータ、サイドチャネルが 公開される場合、ビューは完全なセキュリティ境界ではありません。アプリケーション アカウントには必要な名前空間とコマンドだけを許可します。
A standard view has no independent document-validation schema because it cannot
accept writes. Validation on the source collection constrains writes to that
collection but does not promise that a projection, $lookup, or computed field
matches an application schema forever. Version the view definition and consumer
contract together. The view and every namespace it references must remain in
the same database; a view cannot cross the database namespace boundary.
標準ビューとオンデマンドのマテリアライズドビュー #
新鮮さが重要で基盤クエリが安価な場合は標準ビューが適しています。派生結果が高価でも 更新遅延を許容できる場合、MongoDB は集約パイプラインで生成されたコレクションを オンデマンドのマテリアライズドビュー と呼びます。
db.orders.aggregate([
{ $group: { _id: "$customerId", lifetimeValue: { $sum: "$total" } } },
{ $merge: { into: "customer_lifetime_value", whenMatched: "replace",
whenNotMatched: "insert" } }
])宛先は実際のコレクションなので、インデックスを付けて効率的にクエリできます。
$merge は一致するドキュメントを段階的に置き換えられますが、$out は宛先
コレクションを置き換えます。スケジューラー、変更ストリームコンシューマー、Atlas
Stream Processing パイプライン、またはアプリケーションワークフローが結果を更新
しなければなりません。通常の集約はオンデマンドのマテリアライズドビューを継続的に
維持しないため、新鮮さの契約を明示します。
$merge ジョブが多数のドキュメントを更新すると、読み取り側が部分的に更新された
宛先を観測することがあります。コンシューマーが単一バージョンの可視性を必要とする
場合は、バージョン付きコレクションへ書き込み、検証後に小さなメタデータポインターを
切り替え、古いバージョンを廃止します。重複ストレージ、インデックス構築、更新中の
変更捕捉、クリーンアップ失敗を運用手順に含めます。
コンシューマーが変更ストリームを通じて宛先を監視する必要がある場合は $merge を
使用します。$out で置き換えられたコレクションは、同じマテリアライズドビュー更新
メカニズムとして監視できません。
コメント
GitHub で閲覧・コメントする(投稿にはログインが必要です)