You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MongoDB如何将订单数组项的product字段替换为完整实体数据?

如何将订单中products数组的product字段替换为完整实体数据

需求说明

需要将orders集合中每个订单文档的products数组内,每个元素的product子文档(仅包含_id)替换为products集合中对应的完整产品实体数据,最终得到包含完整产品信息的订单数据。

数据库结构

db={
  "orders": [
    {
      "_id": 1,
      "products": [
        {
          amount: 1,
          product: {
            _id: 1
          }
        },
        {
          amount: 1,
          product: {
            _id: 2
          }
        }
      ]
    },
    {
      "_id": 2,
      "products": [
        {
          amount: 1,
          product: {
            _id: 3
          }
        },
        {
          amount: 1,
          product: {
            _id: 4
          }
        }
      ]
    }
  ],
  "products": [
    {
      "_id": 1,
      "description": "product 1"
    },
    {
      "_id": 2,
      "description": "product 2"
    },
    {
      "_id": 3,
      "description": "product 3"
    },
    {
      "_id": 4,
      "description": "product 4"
    }
  ]
}

期望结果

[
  {
    "_id": 1,
    "products": [
      {
        "amount": 1,
        "product": {
          "_id": 1,
          "description": "product 1"
        }
      },
      {
        "amount": 1,
        "product": {
          "_id": 2,
          "description": "product 2"
        }
      }
    ]
  },
  {
    "_id": 2,
    "products": [
      {
        "amount": 1,
        "product": {
          "_id": 3,
          "description": "product 3"
        }
      },
      {
        "amount": 1,
        "product": {
          "_id": 4,
          "description": "product 4"
        }
      }
    ]
  }
]

正确查询语句

使用MongoDB聚合管道实现关联替换:

db.orders.aggregate([
  // 关联products集合,获取当前订单所有产品的完整信息
  {
    $lookup: {
      from: "products",
      let: { orderProductIds: "$products.product._id" },
      pipeline: [
        {
          $match: {
            $expr: { $in: ["$_id", "$$orderProductIds"] }
          }
        }
      ],
      as: "matchedProducts"
    }
  },
  // 遍历原products数组,替换product字段为完整实体
  {
    $project: {
      products: {
        $map: {
          input: "$products",
          as: "item",
          in: {
            amount: "$$item.amount",
            product: {
              $first: {
                $filter: {
                  input: "$matchedProducts",
                  cond: { $eq: ["$$this._id", "$$item.product._id"] }
                }
              }
            }
          }
        }
      }
    }
  }
])

语句说明

  1. $lookup阶段:

    • 指定关联的集合为products
    • 通过let提取当前订单所有产品的_id列表
    • 在子管道pipeline中筛选出_id属于该列表的产品,存入matchedProducts字段
  2. $project阶段:

    • 使用$map遍历原products数组的每个元素
    • 保留原元素的amount字段,通过$filter从matchedProducts中匹配对应_id的产品,并用$first取出唯一匹配结果,替换原product字段的值

内容的提问来源于stack exchange,提问作者azzlack

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 00:32:39