Mongoose 删除数组中的子文档
Posted
技术标签:
【中文标题】Mongoose 删除数组中的子文档【英文标题】:Mongoose Delete SubDocument in Array 【发布时间】:2021-02-10 14:32:02 【问题描述】:我正在使用 mongoose 为我的项目制作数据库,我的架构 Class
具有如下结构:
const mongoose = require('mongoose')
const classSchema = mongoose.Schema(
_id: mongoose.Schema.Types.ObjectId,
consultant:
type: mongoose.Schema.Types.ObjectId,
ref: 'Consultant',
required: true
,
startYear:
type: String,
required: true
,
classname:
type: String,
required: true,
unique: true
,
studentList: [
code:
type: String,
required: true
,
fullname:
type: String,
required: true
]
)
const Class = mongoose.model('Class', classSchema)
module.exports = Class
如您所见,我有一个名为 studentList
的属性是一个数组,这就是它在 mongoose Atlas 中的存储方式
所以现在我想删除数组studentList
中的一个子文档,所以这是我的路线:
http://localhost:5000/users/:code
这就是我所做的:
exports.delele_student_from_user = (req, res, next) =>
var code = req.params;
var classname = req.body;
User.findOneAndDelete(
classname,
studentList:
$pull:
code,
,
,
)
.exec()
.then((doc) =>
console.log(`deleted user with code $code from colection User`);
next();
)
.catch((err) =>
console.log(err);
return res.status(500).json( err );
);
;
我得到了这个错误:
MongoError: unknown operator: $pull
at MessageStream.messageHandler (C:\Users\ASUS\OneDrive\Desktop\uet-backend\node_modules\mongoose\node_modules\mongodb\lib\cmap\connection.js:266:20)
at MessageStream.emit (events.js:198:13)
at processIncomingData (C:\Users\ASUS\OneDrive\Desktop\uet-backend\node_modules\mongoose\node_modules\mongodb\lib\cmap\message_stream.js:144:12)
at MessageStream._write (C:\Users\ASUS\OneDrive\Desktop\uet-backend\node_modules\mongoose\node_modules\mongodb\lib\cmap\message_stream.js:42:5)
at doWrite (_stream_writable.js:415:12)
at writeOrBuffer (_stream_writable.js:399:5)
at MessageStream.Writable.write (_stream_writable.js:299:11)
at TLSSocket.ondata (_stream_readable.js:709:20)
at TLSSocket.emit (events.js:198:13)
at addChunk (_stream_readable.js:288:12)
at readableAddChunk (_stream_readable.js:269:11)
at TLSSocket.Readable.push (_stream_readable.js:224:10)
at TLSWrap.onStreamRead [as onread] (internal/stream_base_commons.js:94:17)
operationTime:
Timestamp _bsontype: 'Timestamp', low_: 3, high_: 1603874496 ,
ok: 0,
code: 2,
codeName: 'BadValue',
'$clusterTime':
clusterTime:
Timestamp _bsontype: 'Timestamp', low_: 3, high_: 1603874496 ,
signature: hash: [Binary], keyId: [Long] ,
name: 'MongoError'
DELETE /students/16022267 500 785.904 ms - 240
请告诉我如何解决这个问题,非常感谢,祝你有美好的一天
【问题讨论】:
我认为 pull 操作符与findOneAndDelete
操作不兼容。我会尝试updateOne
(因为类名是唯一的)否则拉操作可在数组本身的用户上使用。 studentList.pull(code) 其中 user 是 findeOne(classname) 的结果
【参考方案1】:
你需要使用update
exports.delele_student_from_user = async (req, res, next) =>
var code = req.params;
var classname = req.body;
try
await User.update(
classname ,
$pull:
studentList: code
);
return res.status(200).json( message: "Student deleted" );
catch (err)
return res.status(500).json( err );
;
我也使用了async / await
,所以看起来更干净。
【讨论】:
【参考方案2】:使用 findOneAndUpdate()\
您也可以直接在 MongoDB 中进行更新,而无需加载文档并使用代码对其进行修改。使用 $pull 或 $pullAll 运算符从数组中删除项目。
https://docs.mongodb.com/manual/reference/operator/update/pull/#up._S_pull
【讨论】:
以上是关于Mongoose 删除数组中的子文档的主要内容,如果未能解决你的问题,请参考以下文章
Node.js/mongoose - 数组中的子文档不会删除/移除