我需要将不同集合中的两层编辑的基本记录数据合并

问题描述 投票:0回答:1

我有一个包含一些基本记录数据的集合,例如:

[
  {
    "_id": "one",
    "name": "The Enchanted River",
    "description": "A mystical journey along a forgotten river that holds secrets of a lost civilization.",
    "paperCopy": true,
    "digitalCopy": true,
    "bestSeller": true,
    "isDiscounted": false,
    "discountPercentage": 0.0
  },
  {
    "_id": "two",
    "name": "Galactic Odyssey",
    "description": "An epic space adventure exploring distant galaxies and encountering alien civilizations.",
    "paperCopy": true,
    "digitalCopy": false,
    "bestSeller": true,
    "isDiscounted": false,
    "discountPercentage": 5.57
  },
  {
    "_id": "three",
    "name": "The Last Heir",
    "description": "A gripping tale of a young prince fighting to reclaim his throne against all odds.",
    "paperCopy": true,
    "digitalCopy": true,
    "bestSeller": true,
    "isDiscounted": false,
    "discountPercentage": 27.1
  },
  {
    "_id": "four",
    "name": "Quantum Dreams",
    "description": "A scientist's groundbreaking discovery challenges the very fabric of reality.",
    "paperCopy": true,
    "digitalCopy": true,
    "bestSeller": true,
    "isDiscounted": true,
    "discountPercentage": 22.85
  },
  {
    "_id": "five",
    "name": "The Forgotten Garden",
    "description": "An old gardener unravels the secrets of a mysterious estate with a tragic past.",
    "paperCopy": false,
    "digitalCopy": true,
    "bestSeller": false,
    "isDiscounted": false,
    "discountPercentage": 0.0
  }
]

管理员和用户可以对存储在不同集合中的内容进行编辑。

[
    {
        "_id": "one",
        "user": "admin",
        "patch": {
           bestSeller: false
        }
    },
    {
        "_id": "one",
        "user": "user1",
        "patch": {
           "bestSeller": true,
           "isDiscounted": true,
           "discountPercentage": 99,
           "frontOfStore": true
        }
    },
]

我需要编写一个聚合来将基本记录数据与管理员编辑合并,然后与用户编辑合并,添加以前未定义的字段,并提供查询它们的选项。

mongodb aggregate
1个回答
0
投票
  1. 管理员的第一个

    $lookup
    补丁

    • 如果可以进行多个管理员编辑,请在查找管道中添加排序顺序
  2. 然后

    $lookup
    由用户打补丁;我将非管理员视为用户

    • 如果可以有多个,则按某项排序
  3. $concatArrays
    管理员和用户补丁,以及
    $mergeObjects
    生成的数组以获得最后一个补丁。

    • 决定用户补丁是否应覆盖管理员补丁,相应地在
      concatArrays
      中设置顺序。
    • 无论是 1 个管理员补丁 + 1 个用户补丁还是多个管理员补丁 + 许多用户补丁(0 个、1 个或多个补丁的任意组合),此阶段都将按原样工作。
  4. 将其合并到主文档中并清除多余的字段。

db.books.aggregate([
  {
    // first get admin patches
    $lookup: {
      from: "edits",
      localField: "_id",
      foreignField: "book_id",
      as: "adminEdits",
      pipeline: [
        { $match: { user: "admin" } }
      ]
    }
  },
  {
    // then get user patches (non-admin)
    $lookup: {
      from: "edits",
      localField: "_id",
      foreignField: "book_id",
      as: "userEdits",
      pipeline: [
        { $match: { user: { $ne: "admin" } } }
      ]
    }
  },
  {
    // concat the admin & user patch arrays
    // decide if user edits overwrite admin (concat order)
    // then merge the array of patches sub-objects
    $set: {
      finalPatch: {
        $mergeObjects: {
          $concatArrays: ["$adminEdits.patch", "$userEdits.patch"]
        }
      }
    }
  },
  {
    // merge the result into the doc
    $replaceWith: { $mergeObjects: ["$$ROOT", "$finalPatch"] }
  },
  {
    // remove all the extra fields created in this pipeline
    $unset: ["adminEdits", "userEdits", "finalPatch"]
  }
])

蒙戈游乐场

旁注:您的带有补丁的收藏重复了

_id
对于主键不允许的书籍。所以我在示例和管道中将其称为
book_id

© www.soinside.com 2019 - 2024. All rights reserved.