Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/api/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript MongoDB拒绝大容量(10000)插入/写入的连接_Javascript_Node.js_Mongodb - Fatal编程技术网

Javascript MongoDB拒绝大容量(10000)插入/写入的连接

Javascript MongoDB拒绝大容量(10000)插入/写入的连接,javascript,node.js,mongodb,Javascript,Node.js,Mongodb,我们正在通过Node.js应用程序插入数据,并使用该库连接到mongodb。 Mongo DB共分为5个分片。节点和mongos实例包含在一个四核AWS实例上,该实例具有14980MB的RAM。有两个碎片和配置服务器 包含在单核实例中,其余三个碎片位于具有单核处理器的不同实例上 使用Node.js测试脚本,我们可以在9秒内有效地并发插入1000条记录 对于10000个并发插入,大约2000个插入失败并返回以下错误消息: [Error: failed to connect to [ip a

我们正在通过Node.js应用程序插入数据,并使用该库连接到mongodb。 Mongo DB共分为5个分片。节点和mongos实例包含在一个四核AWS实例上,该实例具有14980MB的RAM。有两个碎片和配置服务器 包含在单核实例中,其余三个碎片位于具有单核处理器的不同实例上

使用Node.js测试脚本,我们可以在9秒内有效地并发插入1000条记录

对于10000个并发插入,大约2000个插入失败并返回以下错误消息:

    [Error: failed to connect to [ip address of mongos]]
在这10000次插入过程中,前5000次或6000次插入成功,没有错误。 在此期间,CPU使用率保持相对较低(13%的使用率)。然后一个核心上的CPU跳到大约75%,MongoDB抛出 拒绝连接的错误消息。插入失败后,某些写入操作会间歇性成功

我们在linux上将ulimit-n设置为20000。我们已经在Node.js api中的insert函数中传递了poolSize=5参数

var responseHandlers = require('./responseHandlers')
    ,schemaValidation = require('./schemaValidation')
    ,mongoDb = require('mongodb')
    ,md5 = require('MD5')
    ,ObjectID = require('mongodb').ObjectID;

function insert(data, timestamp, response) {
  // validating the data to be inserted
  schemaValidation.validate(data, function(err) {
    if(err) {
      console.log(err);
      responseHandlers.invalidRequest(response, 2); 
    } else {
      //console.log("opening db..");
      server = new mongoDb.Server(mongoConfig.host,mongoConfig.port,{'auto_reconnect': true, 'poolSize': 5});
      db = new mongoDb.Db(mongoConfig.database, server, {w: 1});
      db.open(function(err, db) {
        if(err) { 
          console.log(err);
          responseHandlers.invalidRequest(response, 2); 
        } else {
          db.collection(mongoConfig.collection, function(err, collection) {
            if(err) {
              console.log(err);
              responseHandlers.invalidRequest(response, 2); 
            } else {
              //going to instantiate document fields
              var time = new Date().getTime(),
              oid = new ObjectID(),
              hash = md5(oid.toHexString()),
                            obj = {'data_utc' : timestamp, 'server_utc' : time, '_id' : oid,    'hash' : hash}; 
                            obj.data = data;
              //inserting..
              collection.insert(obj, {w:1}, function(err, result) {
                if(err) {
                  console.log(err);
                  responseHandlers.invalidRequest(response, 2); 
                } else {
                  console.log('Insert successful');
                  responseHandlers.validRequest(response, false, result);
                }   
              db.close();
              }); 
            }   
          }); 
        }   
      });   
    }   
  }); 
}   
exports.insert = insert;
有谁能帮我解释一下为什么它会拒绝连接,无法插入?它为什么有效
对于一部分插入,然后在中途失败?

要解决此问题,您应该观察mongod控制台中打开的连接数。根据您提供的代码示例,您可能会在每次插入时打开一个新的mongodb连接。若要更正此问题,请尝试将“服务器”的实例化移动到用于调用此函数的控制循环范围之外。

似乎在循环中创建了太多连接。最好的方法是创建mongoDB客户端的Singleton实例,并在集合中的每次更新和插入都使用相同的对象。 MongoDB对连接池有限制,默认大小为5个连接。之后的任何尝试都将拒绝服务器,但是您可以增加默认连接池大小,但这样做不是一个好主意。
另一点需要注意的是,MongoDB:在执行并发写入的线程数量有限的情况下性能更好。对于集合中的写入(使用最新的驱动程序3.2),mongoDB对集合执行行级锁定。它一次获取1000条记录的锁,并在更新记录时滑动锁。所以,若您放置更多并发线程来执行并行操作,它最终将等待锁被释放。最好使用2个线程进行写操作,或者最大使用4个线程,块大小为20k或40K

您可以考虑为受控读写实现生产者/消费者模式


有关详细信息,请参见此处:

是否为每个插入创建一台服务器(池大小为5),即创建10000 db连接?