我有一個電子商務服務器,我有一個products和一個 orders集合。
任何product檔案都包含一個唯一的productId例如prod_123. 每個order檔案都包含一個lineItems(陣列)欄位,該欄位回傳已productId購買產品的 s 以及相應購買的產品,quantity例如
[{ productId: 'prod_123', quantity: 2 }, { productId: 'prod_234', quantity: 7 }, ...]
當我的客戶獲取他們的訂單時,我想用集合中匹配的產品檔案填充每個lineItems元素。productIdproducts
我已經撰寫了一個 mongoDB 聚合管道來實作這一點,到目前為止就是這樣:
const orderPipeline = [
{
$match: { customerId: 'the customer's ID' },
},
{
$lookup: {
from: 'products',
let: { productIds: '$lineItems.productId' },
pipeline: [
{ $match: { $expr: { $in: ['$productId', '$$productIds'] } } },
//*** somehow, need to add in corresponding `lineItem.quantity` here
],
as: 'products',
},
},
{ $unset: ['lineItems'] },
];
但是,正如您所看到的,雖然正在加入,但在洗掉之前,我無法弄清楚如何將匹配的產品添加到加入的產品quantity中。productlineItems
如何添加對應quantity的匹配項product?
uj5u.com熱心網友回復:
考慮到評論中提到的其他約束,我很確定會起作用的一種方法是利用operator。總的來說,它會像這樣作業:$zip
- 使用從其他集合中檢索到的資訊執行
$lookup生成陣列 ( )。products - 使用
$addFields階段作為大多陣列合邏輯發生的地方。它將$zip兩個陣列放在一起,然后$map將它的$mergeObjects每一對組合成一個物件。 - 完成一個
$unset階段以洗掉原始lineItems欄位(已合并到重新創建的products陣列中。
完整的管道看起來像這樣:
db.orders.aggregate([
{
$match: {
customerId: 123
},
},
{
$lookup: {
from: "products",
let: {
productIds: "$lineItems.productId"
},
pipeline: [
{
$match: {
$expr: {
$in: [
"$productId",
"$$productIds"
]
}
}
}
],
as: "products",
}
},
{
"$addFields": {
"products": {
"$map": {
"input": {
"$zip": {
"inputs": [
"$lineItems",
"$products"
]
}
},
"in": {
"$mergeObjects": "$$this"
}
}
}
}
},
{
$unset: "lineItems"
}
])
游樂場示例在這里
The $mapand the$mergeObjects: "$$this"乍一看可能看起來很奇怪。這是必需的,因為$zip它將生成一個陣列陣列(每個陣列有 2 個條目),例如:
"zipped": [
[
{
"productId": "a",
"quantity": 1
},
{
"_id": ObjectId("5a934e000102030405000002"),
"productId": "a"
}
],
[
{
"productId": "b",
"quantity": 2
},
{
"_id": ObjectId("5a934e000102030405000003"),
"productId": "b"
}
],
[
{
"productId": "c",
"quantity": 3
},
{
"_id": ObjectId("5a934e000102030405000004"),
"productId": "c"
}
]
]
(這是一個游樂場鏈接,顯示了壓縮后但在進一步處理之前的輸出。)
因此,我們需要將它們中的每一個折疊成一個物件,因此$mergeObjects. 外部陣列中的每個物件都是一個陣列(與我們要合并的兩個物件)這一事實是我們可以簡單地"$$this"用作運算子的輸入運算式的原因。
轉載請註明出處,本文鏈接:https://www.uj5u.com/ruanti/533119.html
上一篇:Mongoose不會填充到陣列中
