node.js mongoError:拓扑被破坏
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/30909492/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
mongoError: Topology was destroyed
提问by dreagan
I have a REST service built in node.js with Restify and Mongoose and a mongoDB with a collection with about 30.000 regular sized documents. I have my node service running through pmx and pm2.
我有一个在 node.js 中构建的 REST 服务,带有 Restify 和 Mongoose,还有一个 mongoDB,其中包含一个包含大约 30.000 个常规大小文档的集合。我的节点服务通过 pmx 和 pm2 运行。
Yesterday, suddenly, node started crapping out errors with the message "MongoError: Topology was destroyed", nothing more. I have no idea what is meant by this and what could have possibly triggered this. there is also not much to be found when google-searching this. So I thought I'd ask here.
昨天,突然,节点开始用消息“MongoError:拓扑被破坏”来解决错误,仅此而已。我不知道这是什么意思,什么可能触发了这个。谷歌搜索时也找不到太多东西。所以我想我会在这里问。
After restarting the node service today, the errors stopped coming in. I also have one of these running in production and it scares me that this could happen at any given time to a pretty crucial part of the setup running there...
今天重新启动节点服务后,错误不再出现。我也在生产中运行了其中一个,这让我感到害怕,这可能会在任何给定时间发生在那里运行的设置的一个非常关键的部分......
I'm using the following versions of the mentioned packages:
我正在使用上述软件包的以下版本:
- mongoose: 4.0.3
- restify: 3.0.3
- node: 0.10.25
- 猫鼬:4.0.3
- 修复:3.0.3
- 节点:0.10.25
采纳答案by Jason Nichols
It seems to mean your node server's connection to your MongoDB instance was interrupted while it was trying to write to it.
这似乎意味着您的节点服务器与 MongoDB 实例的连接在尝试写入时中断。
Take a look at the Mongo source code that generates that error
Mongos.prototype.insert = function(ns, ops, options, callback) {
if(typeof options == 'function') callback = options, options = {};
if(this.s.state == DESTROYED) return callback(new MongoError(f('topology was destroyed')));
// Topology is not connected, save the call in the provided store to be
// Executed at some point when the handler deems it's reconnected
if(!this.isConnected() && this.s.disconnectHandler != null) {
callback = bindToCurrentDomain(callback);
return this.s.disconnectHandler.add('insert', ns, ops, options, callback);
}
executeWriteOperation(this.s, 'insert', ns, ops, options, callback);
}
This does not appear to be related to the Sails issue cited in the comments, as no upgrades were installed to precipitate the crash or the "fix"
这似乎与评论中引用的 Sails 问题无关,因为没有安装升级来加速崩溃或“修复”
回答by Adrien Joly
I know that Jason's answer was accepted, but I had the same problem with Mongoose and found that the service hosting my database recommended to apply the following settingsin order to keep Mongodb's connection alive in production:
我知道 Jason 的回答被接受了,但我在 Mongoose 上遇到了同样的问题,并发现托管我的数据库的服务建议应用以下设置,以便在生产中保持 Mongodb 的连接:
var options = {
server: { socketOptions: { keepAlive: 1, connectTimeoutMS: 30000 } },
replset: { socketOptions: { keepAlive: 1, connectTimeoutMS: 30000 } }
};
mongoose.connect(secrets.db, options);
I hope that this reply may help other people having "Topology was destroyed" errors.
我希望这个回复可以帮助其他有“拓扑被破坏”错误的人。
回答by gafi
This error is due to mongo driver dropping the connection for any reason (server was down for example).
此错误是由于 mongo 驱动程序出于任何原因断开连接(例如服务器已关闭)。
By default mongoose will try to reconnect for 30 seconds then stop retrying and throw errors forever until restarted.
默认情况下,猫鼬会尝试重新连接 30 秒,然后停止重试并永远抛出错误,直到重新启动。
You can change this by editing these 2 fields in the connection options
您可以通过在连接选项中编辑这 2 个字段来更改此设置
mongoose.connect(uri,
{ server: {
// sets how many times to try reconnecting
reconnectTries: Number.MAX_VALUE,
// sets the delay between every retry (milliseconds)
reconnectInterval: 1000
}
}
);
回答by Carlos Rodríguez
In my case, this error was caused by a db.close();out of a 'await' section inside of 'async'
在我的情况下,这个错误是由db.close();“async”中的“await”部分引起的
MongoClient.connect(url, {poolSize: 10, reconnectTries: Number.MAX_VALUE, reconnectInterval: 1000}, function(err, db) {
// Validate the connection to Mongo
assert.equal(null, err);
// Query the SQL table
querySQL()
.then(function (result) {
console.log('Print results SQL');
console.log(result);
if(result.length > 0){
processArray(db, result)
.then(function (result) {
console.log('Res');
console.log(result);
})
.catch(function (err) {
console.log('Err');
console.log(err);
})
} else {
console.log('Nothing to show in MySQL');
}
})
.catch(function (err) {
console.log(err);
});
db.close(); // <--------------------------------THIS LINE
});
回答by codeinaire
Just a minor addition to Gaafar's answer, it gave me a deprecation warning. Instead of on the server object, like this:
只是 Gaafar 回答的一个小补充,它给了我一个弃用警告。而不是在服务器对象上,像这样:
MongoClient.connect(MONGO_URL, {
server: {
reconnectTries: Number.MAX_VALUE,
reconnectInterval: 1000
}
});
It can go on the top level object. Basically, just take it out of the server object and put it in the options object like this:
它可以放在顶级对象上。基本上,只需将它从服务器对象中取出并放入选项对象中,如下所示:
MongoClient.connect(MONGO_URL, {
reconnectTries: Number.MAX_VALUE,
reconnectInterval: 1000
});
回答by golfadas
"Topology was destroyed" might be caused by mongoose disconnecting before mongo document indexes are created, per this comment
“拓扑被破坏”可能是由猫鼬在创建 mongo 文档索引之前断开连接引起的,根据此评论
In order to make sure all models have their indexes built before disconnecting, you can:
为了确保所有模型在断开连接之前都建立了索引,您可以:
await Promise.all(mongoose.modelNames().map(model => mongoose.model(model).ensureIndexes()));
await mongoose.disconnect();
回答by Black Mamba
Sebastian comment on Adrien's answer needs more attention it helped me but it being a comment might be ignore sometime so here's a solution:
塞巴斯蒂安对阿德里安回答的评论需要更多关注,它对我有帮助,但它作为评论有时可能会被忽略,所以这里有一个解决方案:
var options = { useMongoClient: true, keepAlive: 1, connectTimeoutMS: 30000, reconnectTries: 30, reconnectInterval: 5000 }
mongoose.connect(config.mongoConnectionString, options, (err) => {
if(err) {
console.error("Error while connecting", err);
}
});
回答by Thavaprakash Swaminathan
Here what I did, It works fine. Issue was gone after adding below options.
这是我所做的,它工作正常。添加以下选项后问题消失了。
const dbUrl = "mongodb://localhost:27017/sampledb";
const options = { useMongoClient: true, keepAlive: 1, connectTimeoutMS: 30000, reconnectTries: 30, reconnectInterval: 5000, useNewUrlParser: true }
mongoose.connect(dbUrl,options, function(
error
) {
if (error) {
console.log("mongoerror", error);
} else {
console.log("connected");
}
});
回答by tkrizsa
I met this in kubernetes/minikube + nodejs + mongoose environment. The problem was that DNS service was up with a kind of latency. Checking DNS is ready solved my problem.
我在 kubernetes/minikube + nodejs + mongoose 环境中遇到了这个。问题在于 DNS 服务存在某种延迟。检查 DNS 已准备好解决了我的问题。
const dns = require('dns');
var dnsTimer = setInterval(() => {
dns.lookup('mongo-0.mongo', (err, address, family) => {
if (err) {
console.log('DNS LOOKUP ERR', err.code ? err.code : err);
} else {
console.log('DNS LOOKUP: %j family: IPv%s', address, family);
clearTimeout(dnsTimer);
mongoose.connect(mongoURL, db_options);
}
});
}, 3000);
var db = mongoose.connection;
var db_options = {
autoReconnect:true,
poolSize: 20,
socketTimeoutMS: 480000,
keepAlive: 300000,
keepAliveInitialDelay : 300000,
connectTimeoutMS: 30000,
reconnectTries: Number.MAX_VALUE,
reconnectInterval: 1000,
useNewUrlParser: true
};
(the numbers in db_options are arbitrary found on stackoverflow and similar like sites)
(db_options 中的数字是在 stackoverflow 和类似站点上任意找到的)
回答by lutaoact
I alse had the same error. Finally, I found that I have some error on my code. I use load balance for two nodejs server, but I just update the code of one server.
我也有同样的错误。最后,我发现我的代码有一些错误。我对两台 nodejs 服务器使用负载均衡,但我只更新了一台服务器的代码。
I change my mongod server from standalone to replication, but I forget to do the corresponding update for the connection string, so I met this error.
我换了我的mongod服务器from standalone to replication,但是忘记对连接字符串做相应的更新,所以遇到了这个错误。
standalone connection string:
mongodb://server-1:27017/mydb
replication connection string:
mongodb://server-1:27017,server-2:27017,server-3:27017/mydb?replicaSet=myReplSet
独立连接字符串:
mongodb://server-1:27017/mydb
复制连接字符串:
mongodb://server-1:27017,server-2:27017,server-3:27017/mydb?replicaSet=myReplSet
details here:[mongo doc for connection string]

