MongoDB聚合管道project阶段排除动态嵌套对象属性求助
MongoDB聚合管道隐藏动态嵌套属性解决方案
核心思路
$project 无法直接操作对象内的动态键,因此通过$objectToArray + $arrayToObject的组合处理type=2题目中的emq嵌套动态对象,同时保留原有type=1题目的答案隐藏逻辑,无需修改现有数据结构。
完整修改后的聚合管道
将$lookup下的pipeline替换为以下内容即可:
[ { $match: { $expr: { $eq: ['$_id', '$$question_id'], }, }, }, // 处理type=2的emq动态嵌套字段 { $addFields: { emq: { $cond: { if: { $eq: ['$type', '2'] }, then: { $arrayToObject: { $map: { input: { $objectToArray: '$emq' }, as: 'emqItem', in: { k: '$$emqItem.k', // 仅保留需要的question字段,自动丢弃answer、explanation v: { question: '$$emqItem.v.question' } } } } }, else: '$emq' } } } }, // 最终字段投影 { $project: { // 全局排除顶层answer字段,type=2题目无该字段无副作用 answer: 0, Description: 1, options: 1, type: 1, emq: 1, score: 1, } } ]
逻辑说明
- 顶层
answer字段直接设置为0全局排除,不需要额外加条件判断,适配所有题型 type=2的emq字段处理流程:- 用
$objectToArray将动态键的emq对象转换为[{k: 键名, v: 值对象}]格式的数组 - 用
$map遍历数组,对每个嵌套子对象仅保留需要的字段 - 用
$arrayToObject将处理后的数组转回原结构的对象
- 用
- 适配MongoDB 3.4及以上版本,若使用4.2及以上版本,也可将
v的构造逻辑替换为$removeFields实现更灵活的字段删除:v: { $removeFields: ['$$emqItem.v', ['answer', 'explanation']] }
内容的提问来源于stack exchange,提问作者dev_2k20
相关产品推荐
相关产品推荐

