节点.js。创建连接的正确/最佳实践

Posted

技术标签:

【中文标题】节点.js。创建连接的正确/最佳实践【英文标题】:Node js. Proper / Best Practice to create connection 【发布时间】:2017-05-17 05:00:03 【问题描述】:

现在我正在 Node JS 中创建一个非常大的应用程序。我正在努力使我的代码简洁明了(就像大多数开发人员一样)。我创建了自己的 js 文件来处理与 mysql 的连接。请看下面的代码。

var mysql = require('mysql');

var config = 
    'default' : 
        connectionLimit : process.env.DB_CONN_LIMIT,
        host     : process.env.DB_HOST,
        user     : process.env.DB_USER,
        password : process.env.DB_PASS,
        database : process.env.DB_NAME,
        debug    : false,
        socketPath  : process.env.DB_SOCKET
    
;

function connectionFunc(query,parameters,callback,configName) 

    configName = configName || "default";

    callback = callback || null;

    parameters = parameters;

    if(typeof parameters == 'function')

        callback = parameters;

        parameters = [];

    
    //console.log("Server is starting to connect to "+configName+" configuration");
    var dbConnection = mysql.createConnection(config[configName]);

    dbConnection.connect();

    dbConnection.query(query,parameters, function(err, rows, fields) 
      //if (!err)
        callback(err,rows,fields);
      //else
        //console.log('Error while performing Query.');
    );

    dbConnection.end();


module.exports.query = connectionFunc;

我在我的模型中使用上述文件,如下所示:

var database = require('../../config/database.js');

module.exports.getData = function(successCallBack)
    database.query('SAMPLE QUERY GOES HERE', function(err, result)
        if(err) console.log(err)
        //My statements here
    );

使用这种编码风格,一切正常,但是当我试图创建一个函数时,由于某种原因循环我的模型的方法。请参阅下面的示例:

for (i = 0; i < 10000; i++) 
    myModel.getData(param, function(result)             
        return res.json(data : result ); 
    );

它给了我一个ER_CON_COUNT_ERROR : Too Many Conenction。问题是当我的连接总是被这个dbConnection.end(); 终止时,为什么我仍然会收到这样的错误?我仍然不确定我是否遗漏了什么。我仍然坚持这一点。 我的连接限制是 100,我认为添加更多连接是个坏主意。

【问题讨论】:

尝试使用连接enter link description here希望这有帮助... 感谢您的链接。我已经考虑过这种方法。但是当游泳池由于某种原因被破坏时,我遇到了麻烦。我的应用程序将不再工作。 -_-。 【参考方案1】:

因为从数据库中查询数据是异步的。

在您的循环中,myModel.getData(或更准确地说是下属query)在查询完成之前不会暂停/暂停您的代码,而是将查询发送到数据库服务器,并且一旦数据库响应回调将被调用。

dbConnection 上调用end 不会立即关闭连接,它只会在使用该连接创建的所有查询完成后立即将连接标记为关闭。

mysql: Terminating connections

通过调用 end() 方法可以优雅地终止连接。这将确保所有先前排队的查询在向 MySQL 服务器发送 COM_QUIT 数据包之前仍然存在。

结束连接的另一种方法是调用 destroy() 方法。这将导致底层套接字立即终止。此外,destroy() 保证不会为连接触发更多事件或回调。

但是对于destroy,库不会等待结果,所以结果会丢失,destroy 很少有用。

因此,使用您给定的代码,您尝试一次创建 10000 个连接。

您应该只在 task 的连接上使用,例如如果用户使用浏览器请求数据,那么您应该为此给定请求使用一个连接。定时任务也是如此,如果你有一些任务是在一定的时间间隔内完成的。

这里是一个示例代码:

var database = require('./config/database.js');

function someTask( callback ) 
   var conn = database.getConnection();

   myModel.getData(conn, paramsA, dataReceivedA)

   function dataReceivedA(err, data) 
       myModel.getData(conn, paramsB, dataReceivedB)
   

   function dataReceivedB(err, data) 
      conn.end()
      callback();
   

如果您想在 model 代码中完全隐藏数据库连接。然后你需要做这样的事情:

var conn = myModel.connect();
conn.getData(params, function(err, data) 
   conn.end();
)

如何实际解决这个问题只取决于很多因素,所以这里只能给你提示。

【讨论】:

你的解释让我大开眼界。是的。我真的想在 database.js 中隐藏所有 mysql 连接的代码。我实际上并没有得到你给出的最后一个例子。希望你能多解释一下?

以上是关于节点.js。创建连接的正确/最佳实践的主要内容,如果未能解决你的问题,请参考以下文章

基于K8s插件版的Jenkins动态节点实践内含最佳实践

Node.js 上 MongoDB 连接的最佳实践是啥?

在 Node.js 中管理数据库连接,最佳实践?

main.* 中的 Meteor JS javascript 文件仍然无法正确加载。加载顺序的最佳实践?

笛卡尔连接 (PY)Spark 最佳实践

连接/断开数据库的最佳实践是啥?