異なるスキーマ バージョンを維持する
項目一覧
アプリケーションのスキーマ要件は徐々に変化していく可能性があります。 たとえば、新しいサービスが利用可能になると、ドキュメントに新しいフィールドを追加する必要がある場合があります。 MongoDB の柔軟なデータモデルにより、コレクション全体で非均一のドキュメント構造を使用でき、更新されたスキーマと並行して古いドキュメント構造を保持できます。
スキーマ バージョン管理パターンを使用すると、同じコレクション内に異なるバージョンのスキーマを設定できるため、要件が変更された場合に大規模なスキーマの移行を回避できます。
このタスクについて
ドキュメント内に異なるレベルで表示されるフィールドがある場合、 スキーマ バージョン管理パターン はインデックスに影響を与える可能性があります。 たとえば、同じフィールドを最上位フィールドと異なるドキュメントの埋め込みフィールドとして保存する場合、そのフィールドのクエリをサポートするには複数のインデックスが必要になる場合があります。
始める前に
次の例では、オンラインショップが コレクションを使用して顧客の連絡先情報を追跡しています。 最初は、コレクションには自宅と職場の電話番号のみが含まれています。 時間の経過とともに、新しい連絡先メソッドが追加され、古いメソッドは不要になります。
サンプル ドキュメントを挿入します。
db.contacts.insertOne( { _id: 1, name: "Taylor", home: "209-555-7788", work: "503-555-0110" } )
手順
次の手順では、 コレクションの初期スキーマ バージョンを設定し、別のスキーマを持つ新しいドキュメントを挿入します。
次のステップ
スキーマ バージョン管理パターンを実装した後、アプリケーションがデータをクエリして更新する方法を変更する必要があります。
コレクションをクエリする
contacts
コレクションには 2 つの異なるスキーマがあるため、クエリは、ドキュメントのスキーマ バージョンに応じて、フィールド値の可能なすべてのロケーションを確認する必要があります。
次のクエリは、カスタマーのwork
番号に基づいて検索します。 クエリは、 work
フィールドが利用可能な両方の場所を確認します。
db.contacts.find( { $or: [ { work: "503-555-0110" }, { "contactInfo.work": "503-555-0110" } ] } )
出力:
{ _id: 1, name: 'Taylor', home: '209-555-7788', work: '503-555-0110', schemaVersion: 1 }
コレクション内のドキュメントを更新する
データの挿入と同様に、コレクションを更新する際、アプリケーションは更新されるフィールドが利用可能なすべての場所を確認する必要があります。 データを更新するときは、 schemaVersion
フィールドを使用して更新するフィールドを決定できます。
_id: 2
を使用してユーザーのwork
の電話番号を更新するには、次のコマンドを実行します。
db.contacts.updateOne( { _id: 2 }, [ { $set: { "work": { $cond: { if: { $eq: [ "$schemaVersion", 1 ] }, then: "999-999-9999", else: null } }, "contactInfo.work": { $cond: { if: { $eq: [ "$schemaVersion", 2 ] }, then: "999-999-9999", else: null } } } } ] )
前の例では、次のようになります。
一致したドキュメントの
schemaVersion
が1
の場合、work
フィールドには更新された値が設定されます。一致したドキュメントの
schemaVersion
が2
の場合、contactInfo.work
フィールドには更新された値が設定されます。