node-postgres:连接过多时ECONNREFUSED

时间:2018-11-13 17:22:25

标签: node.js postgresql express concurrency connection-pooling

我为 nodejs express应用开发了一个简单的资源。我正在使用brianc的node-postgres客户端来处理与我的 postgres 数据库的连接。遵循documentation中的 async / await 样式,我的users.js控制器应如下所示:

代码:

const { Pool } = require('pg');
const pool = new Pool();

module.exports = {
    index: async (req, res, next) => {
        try {
            const dbResult = await pool.query(`select * from users`, []);
            //do stuff with the data here and return response
        } catch (err) {
            next(err);
        }
    }
}

我相信该资源非常简单,并且可以正常工作。但是,我想使用loadtest使用此端点对服务器进行负载测试。我使用

使用并发100并以200个请求/秒的速度进行了测试

负载测试:

loadtest -H authorization:(sometoken) -c 100 --rps 200 http://localhost:3000/users

在进行负载测试时,我将运行节点应用程序并查看控制台。前几百个请求将状态200精细化,而不久之后,我将在大多数请求中得到错误 ECONNREFUSED 。错误率通常为请求总数的 62%(当然,较低的错误率也可以)。

enter image description here

初步发现:

我做了很多谷歌搜索,反复试验。我发现ECONNREFUSED是连接限制被最大化的结果。但是我认为连接池应该可以处理它,因为它可以回收/重用客户端/连接。

我还尝试过修改 postgresql.conf ,设置max_connections = n,shared_buffers = nGB,尝试了不同的配置,但没有一个起作用,错误率会相同。

尝试了不同的样式,基于promise的,回调的,并且对于loadtest我仍然得到相同的错误率。尝试使用 connectionTimeoutMillis 参数进行修补,并且没有任何变化。

我相信以200 rps和100并发率中断对于诸如简单选择查询之类的简单资源是不利的。如果是机器限制,我使用的是相当不错的机器-Core i7 6700、16GB DDR4。我错过了什么还是我做错了吗?谢谢!

1 个答案:

答案 0 :(得分:0)

按照node-pool中所述检查您的池配置。假设数据库能够接受101个连接(并发+开发人员的查询浏览器:),则应设置max=100来应对100个并发。
为了进行微调以避免等待资源,可能需要考虑acquireTimeoutMillismaxWaitingClients的价值。