MongoDB如何在字段不存在时赋值,存在时保留原值
MongoDB 实现更新时仅当tempId不存在才赋值的操作
原始文档
{ "_id" : ObjectId("6336d94e0330f5d48e44fb0f"), "systemId" : "5124301", "userId" : "9876543210", "tempId" : "123456da87sdafasdf", "updatedAt" : ISODate("2022-09-30T12:01:11.714+0000"), "receivedAt" : ISODate("2022-04-10T23:15:08.145+0000"), }
需求说明
更新文档的userId、receivedAt等字段时,仅当tempId字段不存在时为其赋值;若tempId已存在,则保持原值不变。
预期更新结果
场景1:tempId已存在时
更新后tempId保留原值,仅修改userId:
{ "_id" : ObjectId("6336d94e0330f5d48e44fb0f"), "systemId" : "5124301", "userId" : "1234567890", "tempId" : "123456da87sdafasdf", "updatedAt" : ISODate("2022-09-30T12:01:11.714+0000"), "receivedAt" : ISODate("2022-04-10T23:15:08.145+0000"), }
场景2:tempId不存在时
自动为tempId赋值"13qeqrwrqwtqrfsdfweqr",同时修改userId:
{ "_id" : ObjectId("6336d94e0330f5d48e44fb0f"), "systemId" : "5124301", "userId" : "1234567890", "tempId" : "13qeqrwrqwtqrfsdfweqr", "updatedAt" : ISODate("2022-09-30T12:01:11.714+0000"), "receivedAt" : ISODate("2022-04-10T23:15:08.145+0000"), }
错误尝试示例
findOneAndUpdate({ systemId: "5124301" }, { { $set: { userId: "1234567890", receivedAt : ISODate("2022-04-10T23:15:08.145+0000"), tempId: { $exists: then leave it as is, else update it with 13qeqrwrqwtqrfsdfweqr } } } })
错误原因:$exists是查询条件操作符,不能直接用于字段赋值逻辑,不符合MongoDB更新语法。
正确的findOneAndUpdate语句
db.collection.findOneAndUpdate( // 查询条件:匹配指定systemId的文档 { systemId: "5124301" }, // 更新逻辑:使用聚合管道实现条件赋值 [ { $set: { userId: "1234567890", receivedAt: ISODate("2022-04-10T23:15:08.145Z"), // 用$ifNull判断:tempId存在则保留原值,不存在则设置新值 tempId: { $ifNull: ["$tempId", "13qeqrwrqwtqrfsdfweqr"] } } } ], // 可选配置:返回更新后的文档 { returnNewDocument: true } )
说明
- 该方法基于MongoDB 4.2及以上版本的聚合管道更新特性实现
$ifNull表达式会自动检查字段:若tempId存在则返回自身值,不存在则返回指定的新值,从而实现"仅当不存在时赋值"的需求$set操作会确保userId和receivedAt字段被正常更新,不受tempId状态影响
内容的提问来源于stack exchange,提问作者naved17
相关产品推荐
相关产品推荐

