我有两个彼此相关的模型。如果第一个模型的 mongo 文档成功删除,我必须删除其父文档。
尝试执行第二次删除时可能会引发异常,也可能不引发异常。无论是否有错误,我都想连接第一条和第二条消息,但“findOneAndDelete”内的“message”变量的范围与其父级不同。
如何实现这个要求?
下面的代码片段工作正常,但仅传递了主要消息。
var id = req.params.id;
var valid = mongoose.Types.ObjectId.isValid(id);
if (valid) {
MyModel
.findByIdAndDelete({"_id": id})
.exec(function (err, result) {
var message = "Item has been removed successful.";
if (!result) {
message = "Error at deleting an about item.";
} else {
// finding and deleting related about image item
var query = { "id": id };
SecondModel
.findOneAndDelete(query).exec(function (err, result) {
// deletion is OK, but the concatenation does not work
// how to return this "message" scope to its parent?
message += " Image item has been removed successful.";
if (!result) {
message += " Error trying to remove about image item.";
}
});
}
// the concatenation should be returned here
responseUtilities.sendJsonResponse(res, err, {"message": message});
});
} else {
responseUtilities.sendJsonResponse(res, false, { "message": "Item id is not valid." });
}
最佳答案
很高兴您找到了答案。这里有一些结构和风格的想法,这些想法将使该代码更易于阅读(将来由您或同事阅读),并使其更易于调试和扩展。首先为两个异步操作构建小型的、 promise 返回的函数。
function deleteAboutWithId(id) {
return new Promise((resolve, reject) => {
AboutModel.findByIdAndDelete({"_id": id}).exec(function (err, result) {
err ? reject(err) : resolve(result)
})
})
}
function deleteImageWithAboutId(id) {
return new Promise((resolve, reject) => {
AboutImageModel.findOneAndDelete({ aboutId: id }).exec(function (err, result) {
err ? reject(err) : resolve(result)
})
})
}
它们的一个很好的好处是它们可以进行单元测试、重用、泛化等。另一个好处是使用它们使您的业务逻辑清晰简洁。代码的读取方式与您向同事描述该函数的方式相同...
- 删除该项目
- 删除图片
- 如果两者都成功,则回复复合成功消息
- 如果其中一个失败,请回答(可能)复合错误消息
公共(public)函数:
const msgIdError = 'About item id is not valid.'
const msgItemSuccess = 'About item has been removed successful.'
const msgImageSuccess = ' Its image item has also been removed successful.'
const msgItemError = 'Error at deleting an about item.'
const msgImageError = ' Error trying to remove about image item.'
module.exports.delete = function (req, res) {
const idAbout = req.params.idAbout
if (!mongoose.Types.ObjectId.isValid(idAbout)) {
responseUtilities.sendJsonResponse(res, false, { "message": msgIdError })
}
let message = ''
deleteAboutWithId(idAbout).then(() => {
message += msgItemSuccess
return deleteImageWithAboutId(idAbout)
}).then(() => {
message += msgImageSuccess
responseUtilities.sendJsonResponse(res, err, { "message": message })
}).catch(err => {
// if message is empty, the first block threw the error
message += message.length ? msgImageError : msgItemError
responseUtilities.sendJsonResponse(res, err, { "message": message });
})
}
一些简短的说明:(1) 很好地摆脱了字符串的干扰。这些可能有一天会保留在配置中,翻译成其他语言等。 (2) 它会稍微清理一下代码,以检查顶部的无效输入,如果输入无效,则在顶部退出。
关于javascript - 如何在 Node.js 中通过 Mongoose 连接通过两个回调调用创建的字符串?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60424686/