具有 pm2 的节点集群每隔一个请求排队

Node clusters with pm2 queues every other request

我正在使用 pm2 来管理对我的 API 的并发请求,到目前为止一切顺利,我已经设法让它工作了。

我的api只有一条路线。每个请求需要 1-2 分钟才能完全解决并发回响应。一旦我发出第一个请求,我就可以在 pm2 日志中看到该请求已被接受,但是如果我向同一路由发出第二个请求,它就会排队,并且只有在第一个请求完成后才会被处理。 只有在第二个请求在队列中时我向同一路由发出第三个请求时,才会调用另一个工作人员并接受第三个请求,第二个工作人员会留在队列中,直到第一个请求得到解决。 我希望我说清楚了

第一个请求被一个工人迅速接受,第二个请求排队,第三个请求也被另一个工人迅速接受,第四个排队,第五个被接受,第六个排队等。

我有 24 个可用的工人。

这是我非常简单的服务器:

const express = require('express');
const runner = require('./Rrunner2')
const moment = require('moment');
const bodyParser = require('body-parser');



const app = express();
app.use(express.json({limit: '50mb', extended: true}));
app.use(bodyParser.json())


app.post('/optimize', (req, res) => {
    try{
        
        const req_start = moment().format('DD/MM/YYYY h:mm a');
        console.log('Request received at ' + req_start)
        console.log(`Worker process ID - ${process.pid} has accepted the request.`);
    
        const data = req.body;
        
        const opt_start = moment().format('DD/MM/YYYY h:mm a')
        console.log('Optimization started at ' + opt_start)
        let result = runner.optimizer(data);

        const opt_end = moment().format('DD/MM/YYYY h:mm a')
        console.log('Optmization ended at ' + opt_end)
        
        const res_send = moment().format('DD/MM/YYYY h:mm a');
        console.log('Response sent at ' + res_send)
        return res.send(result)

    }catch(err){
        console.error(err)
        return res.status(500).send('Server error.')
    }


});

const PORT = 3000;
app.listen(PORT, () => console.log(`Server listening port ${PORT}.`))

我的 PM2 生态系统文件是:

module.exports = {
  apps : [{
    name: "Asset Optimizer",
    script: "server.js",
    watch: true,
    ignore_watch: ["optimizer", "outputData", "Rplots.pdf", "nodeSender.js", "errorLog"],
    instances: "max",
    autorestart: true,
    max_memory_restart: "1G",
    exec_mode: "cluster",
    watch_options:{
      "followSymlinks": false
      }
    }
  ]}

我使用 pm2 start ecosystem.config.js

启动服务器

一切正常,但这个队列问题让我抓狂。我尝试过很多肮脏的方法,包括拆分路由、拆分服务器。没有任何成功。

即使你不知道这个问题的答案,也请给我一些关于如何克服这个问题的想法。非常感谢。

更新

好的,我已经设法通过设置使它与本机集群模块一起工作:

const cluster = require('cluster');
const http = require('http');
const numCPUs = require('os').cpus().length;

cluster.schedulingPolicy = cluster.SCHED_RR;

但是一旦我尝试让 pm2 启动服务器,它就不再起作用了。 有没有可能让pm2接受Round Robin appproach

P.S.: 我正在使用windows,在节点文档中发现默认情况下没有设置它是onlu平台。

此问题唯一可行的解​​决方案是将 nginx 实施为反向代理和负载平衡器。

我使用的是 nginx 1.18.0,这是让它工作的配置文件。 如果有人遇到这个问题,nginx + pm2 是可行的方法。 如果有人遇到这个问题,很高兴进一步澄清。它给了我很多工作。

worker_processes  5;
events {
    worker_connections  1024;
}


http {
    include       mime.types;
    default_type  application/octet-stream;

    upstream expressapi {
    least_conn;
    server localhost:3000;
    server localhost:3001;
    server localhost:3002;
    server localhost:3003;
    server localhost:3004;
}


    sendfile        on;

    keepalive_timeout  800;
    fastcgi_read_timeout 800;
    proxy_read_timeout 800;
    

    server {
        listen 8000;

        server_name optimizer;

        location / {
            proxy_pass http://expressapi/;
        }
        

        error_page   500 502 503 504  /50x.html;
        location = /50x.html {
            root   html;
        }

}

如上所述,问题不在于PM2。 Pm2 只是处理发送给它的请求。问题出在发送请求的上层,也就是 nignx。