Javascript Node.js域群集工作程序断开连接

Javascript Node.js域群集工作程序断开连接,javascript,node.js,cluster-computing,node.js-domains,Javascript,Node.js,Cluster Computing,Node.js Domains,查看nodejs域文档页面给出的示例:,使用集群重新启动工作程序的建议方法是调用工作程序部分中的第一个断开连接,并侦听主程序部分中的断开连接事件。但是,如果您只是复制/粘贴给定的示例,您将注意到disconnect()调用不会关闭当前工作进程: 这里发生的是: try { var killtimer = setTimeout(function() { process.exit(1); }, 30000); killtimer.unref(); se

查看nodejs域文档页面给出的示例:,使用集群重新启动工作程序的建议方法是调用工作程序部分中的第一个断开连接,并侦听主程序部分中的断开连接事件。但是,如果您只是复制/粘贴给定的示例,您将注意到disconnect()调用不会关闭当前工作进程:

这里发生的是:

try {
    var killtimer = setTimeout(function() {
        process.exit(1);
    }, 30000);
    killtimer.unref();
    server.close();
    cluster.worker.disconnect();
    res.statusCode = 500;
    res.setHeader('content-type', 'text/plain');
    res.end('Oops, there was a problem!\n');
} catch (er2) {
    console.error('Error sending 500!', er2.stack);
}
  • 我在/处执行get请求错误

    • 计时器启动:30秒后,进程将被终止(如果尚未终止)
    • http服务器已关闭
    • 工作进程已断开连接(但仍处于活动状态)
    • 此时将显示500页
  • 我在错误时执行第二个get请求(30秒之前)

    • 新计时器已启动
    • 服务器已关闭=>引发错误
    • 错误被捕获在“catch”块中,没有结果被发送回客户端,因此在客户端,页面正在等待,没有任何消息
  • 在我看来,最好是杀死这个工人,然后在主部件上再次听到“退出”事件以进行分叉。这样,在发生错误时始终发送500错误:

    try {
        var killtimer = setTimeout(function() {
            process.exit(1);
        }, 30000);
        killtimer.unref();
        server.close();
        res.statusCode = 500;
        res.setHeader('content-type', 'text/plain');
        res.end('Oops, there was a problem!\n');
        cluster.worker.kill();
    } catch (er2) {
        console.error('Error sending 500!', er2);
    }
    
    我不确定使用kill而不是disconnect会有什么副作用,但是disconnect似乎正在等待服务器关闭,但这似乎不起作用(至少不应该这样)

    我只是想得到一些反馈。可能有一个很好的理由,这个例子是这样写的,我错过了

    谢谢

    编辑:

    我刚用curl检查过,效果很好
    然而,我之前使用Chrome进行了测试,似乎在发送回500响应后,Chrome会在服务器实际关闭之前发出第二个请求。
    在这种情况下,服务器正在关闭而未关闭(这意味着工作进程也在断开连接而未断开连接),导致第二个请求与以前一样由同一个工作进程处理,因此:

  • 它阻止服务器完成关闭
  • 第二个
    server.close()正在求值的行,它会触发异常,因为服务器未关闭
  • 在调用killtimer回调之前,以下所有请求都将触发相同的异常

  • 我发现,实际上,当服务器关闭并同时收到请求时,它会停止关闭过程。
    所以他仍然接受连接,但不能再关闭

    即使没有集群,这个简单的示例也说明了这一点:

    var PORT = 8080;
    var domain = require('domain');
    var server = require('http').createServer(function(req, res) {
        var d = domain.create();
        d.on('error', function(er) {
                try {
                    var killtimer = setTimeout(function() {
                        process.exit(1);
                    }, 30000);
                    killtimer.unref();
                    console.log('Trying to close the server');
                    server.close(function() {
                        console.log('server is closed!');
                    });
                    console.log('The server should not now accepts new requests, it should be in "closing state"');
                    res.statusCode = 500;
                    res.setHeader('content-type', 'text/plain');
                    res.end('Oops, there was a problem!\n');
                } catch (er2) {
                    console.error('Error sending 500!', er2);
                }
            });
    
            d.add(req);
            d.add(res);
    
            d.run(function() {
                console.log('New request at: %s', req.url);
                // error
                setTimeout(function() {
                    flerb.bark();
                });
            });
    });
    server.listen(PORT);
    
    只需运行:

    curl http://127.0.0.1:8080/ http://127.0.0.1:8080/ 
    
    输出:

    New request at: /
    Trying to close the server
    The server should not now accepts new requests, it should be in "closing state"
    New request at: /
    Trying to close the server
    Error sending 500! [Error: Not running]
    
    New request at: /
    Trying to close the server
    The server should not now accepts new requests, it should be in "closing state"
    server is closed!
    
    现在单一请求:

    curl http://127.0.0.1:8080/
    
    输出:

    New request at: /
    Trying to close the server
    The server should not now accepts new requests, it should be in "closing state"
    New request at: /
    Trying to close the server
    Error sending 500! [Error: Not running]
    
    New request at: /
    Trying to close the server
    The server should not now accepts new requests, it should be in "closing state"
    server is closed!
    
    例如,chrome为favicon再做一次请求,服务器就无法关闭


    现在,我将继续使用worker.kill(),它使worker不必等待服务器停止。

    我在大约6个月前遇到了同样的问题,遗憾的是,没有任何代码可以演示我以前工作中遇到的问题。我通过显式地向工作人员发送消息并同时调用disconnect解决了这个问题。断开连接可防止工作人员承担新的工作,在我的情况下,由于我正在跟踪工作人员正在做的所有工作(这是针对长期运行上载的上载服务),所以我可以等待所有工作完成,然后使用0退出

    我遇到了同样的问题,断开连接的工作程序仍然收到请求,并且没有关闭。我注意到,在
    killTimer
    过期后,工作进程关闭,而这不应该发生,因为我们
    unref
    计时器,然后完成正常进程,该进程将终止工作进程。正如Node.js文档中所述://但不要为此而保持流程的打开状态<代码>killtimer.unref()我想这可能取决于节点版本,我无法用完全相同的代码重现问题:我的节点版本是0.10.22(我刚刚更新)可运行节点版本是0.10.12