Node.js MongoDB 插入错误
Posted
技术标签:
【中文标题】Node.js MongoDB 插入错误【英文标题】:Node.js MongoDB insert error 【发布时间】:2017-10-18 06:00:59 【问题描述】:function uploadVote(voter, vote)
MongoClient.connect(url, function(err, db)
if (err) throw err;
db.collection('testvote', function(err, collection)
collection.find("psid": voter).toArray(function(err, result)
if(!result[0])
db.collection("testvote").insert(psid: "a", choice:0, function(err, res)
if (err) throw err;
console.log('insertone')
sendTextMessage(". ")
);
else if(!result[0].choice)
db.collection("testvote").update(psid: voter, $set: 'choice': vote, function(err, res)
if (err) throw err;
sendTextMessage(". ")
)
else
sendTextMessage(voter, "!");
);
db.close();
);
)
您好,我正在开发一个让用户投票的 Facebook Messenger。在上面的代码中,我根本看不到语法错误。但是当这个函数被执行时,它总是出错:
/app/node_modules/mongodb/lib/utils.js:123
2017-05-18T12:09:19.856188+00:00 app[web.1]: process.nextTick(function() throw err; );
2017-05-18T12:09:19.856188+00:00 app[web.1]: ^
2017-05-18T12:09:19.858765+00:00 app[web.1]: at ReplSet.insert (/app/node_modules/mongodb/lib/replset.js:398:18)
2017-05-18T12:09:19.858761+00:00 app[web.1]: MongoError: topology was destroyed
2017-05-18T12:09:19.858764+00:00 app[web.1]: at ReplSet.insert (/app/node_modules/mongodb-core/lib/topologies/replset.js:1025:47)
2017-05-18T12:09:19.858766+00:00 app[web.1]: at executeCommands (/app/node_modules/mongodb/lib/bulk/ordered.js:455:23)
2017-05-18T12:09:19.858766+00:00 app[web.1]: at OrderedBulkOperation.execute (/app/node_modules/mongodb/lib/bulk/ordered.js:508:10)
2017-05-18T12:09:19.858767+00:00 app[web.1]: at bulkWrite (/app/node_modules/mongodb/lib/collection.js:664:8)
2017-05-18T12:09:19.858768+00:00 app[web.1]: at Collection.insertMany (/app/node_modules/mongodb/lib/collection.js:534:44)
2017-05-18T12:09:19.858769+00:00 app[web.1]: at /app/index.js:121:41
2017-05-18T12:09:19.858768+00:00 app[web.1]: at Collection.insert (/app/node_modules/mongodb/lib/collection.js:836:15)
2017-05-18T12:09:19.858770+00:00 app[web.1]: at handleCallback (/app/node_modules/mongodb/lib/utils.js:120:56)
2017-05-18T12:09:19.858771+00:00 app[web.1]: at /app/node_modules/mongodb/lib/cursor.js:860:16
请帮我解决这个问题。
【问题讨论】:
mongoError: Topology was destroyed的可能重复 我认为您的db.close()
调用可能会在传递给您的 collection.find()
调用的回调之前运行。这意味着在随后的insert()
或update()
调用开始时,数据库连接已经关闭
感谢您的帮助!那我应该如何编辑我的代码?
只需将 db.close() 放入回调中
您需要确保 db.close()
仅在您完成后才被调用。您可以将它放在每个代码分支的末尾(即在 sendTextMessage()
的每个案例之后),或者将整个内容包装在一个 promise 中,然后在这些位置调用 resolve。我会在下面写一个答案。
【参考方案1】:
如果您收到这样的MongoError: topology was destroyed
,则表示您与 MongoDB 服务器的连接已中断。确保您有良好的连接并且在您运行查询时它正在运行。
【讨论】:
哦,谢谢。我正在使用 MongoDB Atlas,也许这有问题。我再试一次后能再给我一个建议吗?顺便说一句,我非常感谢您的帮助。【参考方案2】:数据库调用将是异步的,这意味着db.close()
行将在回调内的代码之前运行。
您需要确保db.close()
仅在您完成连接后才被调用。您可以将它放在每个代码分支的末尾(即在 sendTextMessage()
的每个案例之后),或者将整个内容包装在一个 Promise 中,然后在这些位置调用 resolve。
这是一个包含在 Promise 中的代码版本。 resolve()
方法仅在您知道不再需要发出请求时调用。您也不能将它包装在一个承诺中,并在我放置了 resolve()
声明的每个地方放置一个 db.close()
声明。
function uploadVote(voter, vote)
MongoClient.connect(url, function(err, db)
if (err) throw err;
new Promise((resolve, reject) =>
db.collection('testvote', function(err, collection)
collection.find("psid": voter).toArray(function(err, result)
if(!result[0])
db.collection("testvote").insert(psid: "a", choice:0, function(err, res)
if (err) throw err;
console.log('insertone')
sendTextMessage(". ")
resolve();
);
else if(!result[0].choice)
db.collection("testvote").update(psid: voter, $set: 'choice': vote, function(err, res)
if (err) throw err;
sendTextMessage(". ")
resolve();
)
else
sendTextMessage(voter, "!");
resolve();
);
);
).then(() => db.close());
)
【讨论】:
np。另外,我只是想您可能想将.then(() => db.close())
更改为 .finally(() => db.close())
并将 throw 语句更改为 reject(err)
。这应该确保即使您出错,连接也会关闭。无论承诺是解决还是拒绝,.finally
都会运行。以上是关于Node.js MongoDB 插入错误的主要内容,如果未能解决你的问题,请参考以下文章
在使用 node.js 完成所有承诺后,我想在 mongodb 中插入数据
Node.js + MongoDB:插入一个并返回新插入的文档