【问题标题】:How to debug a socket hang up error in NodeJS?如何调试 NodeJS 中的套接字挂起错误?
【发布时间】:2012-06-04 13:57:41
【问题描述】:

我收到以下错误:

events.js:48
        throw arguments[1]; // Unhandled 'error' event
        ^
Error: socket hang up
    at createHangUpError (http.js:1091:15)
    at Socket.onend (http.js:1154:27)
    at TCP.onread (net.js:363:26)

在节点 v0.6.6 中,我的代码有多个 http.request 和 .get 调用。 请提出一些方法来跟踪导致套接字挂起的原因,以及它是在哪个请求/调用上。 谢谢

【问题讨论】:

  • 你可以通过重启服务器来解决,我们正在使用pm2,当我们得到上面的错误我们做pm2 restart all

标签: node.js sockets http debugging


【解决方案1】:

快速而肮脏的开发解决方案

使用longjohn,您将获得包含异步操作的长堆栈跟踪。

清洁正确的解决方案: 从技术上讲,在节点中,只要you emit an 'error' event and no one listens to it, it will throw。为了让它不抛出,在它上面放一个监听器并自己处理它。这样您就可以记录错误并提供更多信息。

要为一组调用设置一个监听器,您可以使用domains 并在运行时捕获其他错误。确保与 http(Server/Client) 相关的每个异步操作与代码的其他部分相比位于不同的domain 上下文中,域将自动侦听error 事件并将其传播到它自己的处理程序。所以你只听那个处理程序并获取错误数据。 You also get more information for free.(域名已弃用)。

正如Mike 建议的那样,您也可以设置NODE_DEBUG=net 或使用strace。它们都为您提供了节点在内部执行的操作。

【讨论】:

  • 然后查看stackoverflow.com/questions/543738/go-to-character-in-vim,了解如何定位跟踪中给出的“pos”。
  • 警告:节点域当前为deprecated
  • 你能展示如何“自己处理”的示例代码吗?如何打印所有相关的堆栈跟踪信息?
  • 基本上添加一个错误处理程序并执行发生错误时应该发生的必要逻辑,大多数时候您只是想记录套接字挂起错误。我建议将它传递给你的日志处理程序,希望它支持打印错误堆栈跟踪,但如果你自己做它通常就像console.log(error) 一样简单
【解决方案2】:

此外,您可以将NODE_DEBUG 环境变量设置为net 以获取有关所有套接字正在做什么的信息。这样您就可以隔离哪个远程资源正在重置连接。

【讨论】:

    【解决方案3】:

    除了ftft1885的回答

    http.get(url, function(res)
    {
        var bodyChunks = [];
    
        res.on('data', function(chunk)
        {
            // Store data chunks in an array
            bodyChunks.push(chunk);
        }).on('error', function(e)
        {
            // Call callback function with the error object which comes from the response
            callback(e, null);
        }).on('end', function()
        {
            // Call callback function with the concatenated chunks parsed as a JSON object (for example)
            callback(null, JSON.parse(Buffer.concat(bodyChunks)));
        });
    }).on('error', function(e) {
        // Call callback function with the error object which comes from the request
        callback(e, null);
    });
    

    当我遇到这个“套接字挂起”错误时,是因为我没有捕捉到请求错误。

    callback 函数可以是任何东西;这一切都取决于您的应用程序的需求。这是使用console.log 记录数据的回调和使用console.error 记录错误的示例:

    function callback(error, data) {
        if (error) {
            console.error('Something went wrong!');
            console.error(error);
        }
        else {
            console.log('All went fine.');
            console.log(data);
        }
    }
    

    【讨论】:

    • 回调函数中应该是什么?我是在服务器上定义还是在响应中提供?
    • 你应该在服务器上定义它
    • @jlewkovich 的第一个问题呢?
    • 如果你改用req.on('error'...,这不是更干净吗?这个想法有问题吗?
    • 这没有错。您可以将从http.get 返回的ClientRequest 存储在一个变量中(比如说req),并使用变量而不是链接添加事件侦听器:const req = http.get(...); req.on('error', ...)
    【解决方案4】:

    使用

    req.on('error',function(err){})
    

    【讨论】:

    • 答案有点短,但重点是:正如 Eschard1991 指出的那样,您不仅需要处理来自响应的错误事件,还需要处理来自请求对象的错误事件。
    【解决方案5】:

    很可能您的服务器套接字连接在所有 http.ServerResponse 对象结束之前以某种方式关闭。确保在处理传入连接之前已停止所有传入请求(传入连接与传入 HTTP 请求不同)。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-09-13
      • 2014-10-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-10-06
      • 2021-07-29
      • 2013-10-05
      相关资源
      最近更新 更多