Mongo DB でコレクションをY栽する

n-ozawan

峻さん、こんにちは。晦永蝕kグル`プの稼-看噛温敬温稼です。
オリンピック易犯していますね。2024定の歪湿オリンピックでは晩云は45倖のメダルを資誼しましたが、書指の喬湿オリンピックは嵎欝磴20倖に曙いていません。この方の餓は、そもそも昇室嶽朕の方が離うことにあります。2024定歪湿オリンピックは32昇室329嶽朕であるのにして、2026定喬湿オリンピックは8昇室116嶽朕です。

云籾です。
RDBではテ`ブル揖平をY栽することができます。Mongo DBでもなるコレクションをY栽することができます。書指はそんなコレクション揖平のY栽圭隈についてまとめました。

Mongo DB Y栽

はじめに

Mongo DB のY栽を_Jする貧で、嚠め參和のデ`タを携襪靴討きます。

db.inventory.insertMany( [
   { prodId: 100, price: 20, quantity: 125 },
   { prodId: 101, price: 10, quantity: 234 },
   { prodId: 102, price: 15, quantity: 432 },
   { prodId: 103, price: 17, quantity: 320 }
] )

db.orders.insertMany( [
   { orderId: 201, custid: 301, prodId: 100, numPurchased: 20 },
   { orderId: 202, custid: 302, prodId: 101, numPurchased: 10 },
   { orderId: 203, custid: 303, prodId: 102, numPurchased: 5 },
   { orderId: 204, custid: 303, prodId: 103, numPurchased: 15 },
   { orderId: 205, custid: 303, prodId: 103, numPurchased: 20 },
   { orderId: 206, custid: 302, prodId: 102, numPurchased: 1 },
   { orderId: 207, custid: 302, prodId: 101, numPurchased: 5 },
   { orderId: 208, custid: 301, prodId: 100, numPurchased: 10 },
   { orderId: 209, custid: 303, prodId: 103, numPurchased: 30 }
] )

Aggregation

$lookup

コレクション揖平を潤栽するには、db.orders.aggregate()のパイプラインにて$lookupで翌何潤栽を佩います。db.orders.aggregate()は云栖、ドキュメントの鹿柴に喘いられる荷恬ですが、コレクション揖平の潤栽にも旋喘することができます。

db.orders.aggregate([
  {
    $lookup: {
      from: "inventory",
      localField: "prodId",
      foreignField: "prodId",
      as: "inventoryDocs"
    }
  }
])

貧芝は、看姻糸艶姻壊コレクションに、$lookup.fromで峺協した庄稼厩艶稼岳看姻霞コレクションを潤栽します。潤栽訳周はlocalFieldforeignFieldで峺協したフィ`ルド揖平が匯崑したドキュメントが潤栽されます。asには潤栽された庄稼厩艶稼岳看姻霞のドキュメント坪否がそのまま鯉追されます。これをg佩すると參和の潤惚が誼られます。

[
  {
    _id: ObjectId('699277eda62e954c728de66a'),
    orderId: 201,
    custid: 301,
    prodId: 100,
    numPurchased: 20,
    inventoryDocs: [
      {
        _id: ObjectId('699277eda62e954c728de666'),
        prodId: 100,
        price: 20,
        quantity: 125
      }
    ]
  },
  ...(參和福待)
]

貧芝の潤惚は庇海であまりよろしくありません。その魁栽は枠ほどの$lookupの朔に、$project$unwindを弖紗します。

db.orders.aggregate([
  {
    $lookup: {
      from: "inventory",
      localField: "prodId",
      foreignField: "prodId",
      as: "inventoryDocs"
    }
  },
  {
    $project: {
      _id: 0,
      orderId: 1,
      custid: 1,
      prodId: 1,
      price: "$inventoryDocs.price"
    }
  },
  { $unwind: "$price" }
])

$projectは卦抜するドキュメントの更撹を壅更廏します。0は掲燕幣、1はそのフィ`ルドを燕幣します。price: "$inventoryDocs.price"では、庄稼厩艶稼岳看姻霞禽看界壊坪の沿姻庄界艶フィ`ルドのみを竃薦するようにします。庄稼厩艶稼岳看姻霞禽看界壊は塘双ですので、$unwindで塘双勣殆をg匯の勣殆に篁擦靴泙后I麓任g佩すると參和の潤惚が誼られます。

[
  { orderId: 201, custid: 301, prodId: 100, price: 20 },
  { orderId: 202, custid: 302, prodId: 101, price: 10 },
  { orderId: 203, custid: 303, prodId: 102, price: 15 },
  { orderId: 204, custid: 303, prodId: 103, price: 17 },
  { orderId: 205, custid: 303, prodId: 103, price: 17 },
  { orderId: 206, custid: 302, prodId: 102, price: 15 },
  { orderId: 207, custid: 302, prodId: 101, price: 10 },
  { orderId: 208, custid: 301, prodId: 100, price: 20 },
  { orderId: 209, custid: 303, prodId: 103, price: 17 }
]

$merge

潤栽とは富し離いますが、$mergeを府初します。$mergeは粥乙乙姻艶乙温岳庄看稼のこれまでの竃薦潤惚を仟しいコレクションに竃薦します。

db.orders.aggregate([
  { /* $lookupなどでY栽 */ },
  { $merge: { into: "ordersWithPrice" } }
])

$merge.intoには恬撹するコレクション兆を峺協します。貧芝をg佩すると看姻糸艶姻壊安庄岳鞄永姻庄界艶コレクションが恬撹されます。書指は福待しましたが、屡に揖じドキュメントが贋壓した魁栽のざなど、屡贋のコレクションにしてどうマ`ジするのかの譜協があります。

$mergeの旋泣は1つの仟しいコレクションを恬撹することです。これにより、その脅業$lookupによる潤栽I尖を佩うことなく、潤栽したコレクションをiみzむことができます。匚寂バッチ吉により協豚議にマ`ジを佩うことで、iみzみ堀業を互堀晒することが覿┐気譴泙后

$mergeの之泣はg悶麗尖デ`タが恬られることです。リソ`スが泙蕕譴討い覲〆呂牢鵑なデメリットになります。

View

閣庄艶敬はコレクションの匯嶽で、g悶麗尖デ`タを隔たない蒙歩なコレクションです。閣庄艶敬の伏撹には粥乙乙姻艶乙温岳庄看稼と揖じ訳周を峺協することができますので、コレクションを潤栽した潤惚を閣庄艶敬として隠隔することができます。

db.createView( "sales", "orders", [
  {
    $lookup: {
      from: "inventory",
      localField: "prodId",
      foreignField: "prodId",
      as: "inventoryDocs"
    }
  },
  {
    $project: {
      _id: 0,
      prodId: 1,
      orderId: 1,
      numPurchased: 1,
      price: "$inventoryDocs.price"
    }
  },
  { $unwind: "$price" }
] )

閣庄艶敬コレクションは、宥械のコレクションと揖じ勣糟で聞うことができます。

db.sales.find()

[
  { orderId: 201, prodId: 100, numPurchased: 20, price: 20 },
  { orderId: 202, prodId: 101, numPurchased: 10, price: 10 },
  { orderId: 203, prodId: 102, numPurchased: 5, price: 15 },
  { orderId: 204, prodId: 103, numPurchased: 15, price: 17 },
  { orderId: 205, prodId: 103, numPurchased: 20, price: 17 },
  { orderId: 206, prodId: 102, numPurchased: 1, price: 15 },
  { orderId: 207, prodId: 101, numPurchased: 5, price: 10 },
  { orderId: 208, prodId: 100, numPurchased: 10, price: 20 },
  { orderId: 209, prodId: 103, numPurchased: 30, price: 17 }
]

閣庄艶敬の屎悶は粥乙乙姻艶乙温岳庄看稼のエイリアスのようなもので、db.collection.aggregate()と來嬬中ではそんなに笋錣蠅泙擦鵝どちらかと冱うと、隠便や砿尖の中でメリットになります。

おわりに

書指は仝潤栽々をテ`マにQいましたが、この粥乙乙姻艶乙温岳庄看稼のパイプラインには謹くの鹿柴荷恬が戻工されています。箭えば、怏岶ツリ`やカテゴリ竣蚊のような壅「議に歌孚を{るのであれば$graphLookupが宴旋ですし、鹸方のコレクションをまとめて碧したい魁栽には$unionWithが宴旋です。もちろん鹿柴荷恬ですので、署駆などの、鮑麓討靴燭蝓▲哀覃`ピングすることもできます。碧の嫌がレがりますね。

ではまた。


Recommendおすすめブログ