node.js - 如何在 Node.js 中调试错误 ECONNRESET?

标签 node.js sockets tcp express

我正在运行一个使用 Socket.io 的 Express.js 应用程序,用于聊天网络应用程序 我在 24 小时内随机收到大约 5 次以下错误。 Node 进程被永远包裹,它会立即重新启动。

问题是重新启动 Express 会将我的用户踢出他们的房间 没有人想要那样。

Web 服务器由 HAProxy 代理。没有套接字稳定性问题, 只使用 websockets 和 flashsockets 传输。 我不能故意复制这个。

这是 Node v0.10.11 的错误:

    events.js:72
            throw er; // Unhandled 'error' event
                  ^
    Error: read ECONNRESET     //alternatively it s a 'write'
        at errnoException (net.js:900:11)
        at TCP.onread (net.js:555:19)
    error: Forever detected script exited with code: 8
    error: Forever restarting script for 2 time

编辑 (2013-07-22)

添加了 socket.io 客户端错误处理程序和未捕获的异常处理程序。 似乎这个捕获了错误:

    process.on('uncaughtException', function (err) {
      console.error(err.stack);
      console.log("Node NOT Exiting...");
    });

所以我怀疑这不是 Socket.io 问题,而是对另一台服务器的 HTTP 请求 我做的或 MySQL/Redis 连接。问题是错误堆栈 不能帮助我识别我的代码问题。这是日志输出:

    Error: read ECONNRESET
        at errnoException (net.js:900:11)
        at TCP.onread (net.js:555:19)

我怎么知道是什么原因造成的?如何从错误中获得更多信息?

好的,不是很冗长,但这是 Longjohn 的堆栈跟踪:

    Exception caught: Error ECONNRESET
    { [Error: read ECONNRESET]
      code: 'ECONNRESET',
      errno: 'ECONNRESET',
      syscall: 'read',
      __cached_trace__:
       [ { receiver: [Object],
           fun: [Function: errnoException],
           pos: 22930 },
         { receiver: [Object], fun: [Function: onread], pos: 14545 },
         {},
         { receiver: [Object],
           fun: [Function: fireErrorCallbacks],
           pos: 11672 },
         { receiver: [Object], fun: [Function], pos: 12329 },
         { receiver: [Object], fun: [Function: onread], pos: 14536 } ],
      __previous__:
       { [Error]
         id: 1061835,
         location: 'fireErrorCallbacks (net.js:439)',
         __location__: 'process.nextTick',
         __previous__: null,
         __trace_count__: 1,
         __cached_trace__: [ [Object], [Object], [Object] ] } }

这里我提供闪存套接字策略文件:

    net = require("net")
    net.createServer( (socket) =>
      socket.write("<?xml version=\"1.0\"?>\n")
      socket.write("<!DOCTYPE cross-domain-policy SYSTEM \"http://www.macromedia.com/xml/dtds/cross-domain-policy.dtd\">\n")
      socket.write("<cross-domain-policy>\n")
      socket.write("<allow-access-from domain=\"*\" to-ports=\"*\"/>\n")
      socket.write("</cross-domain-policy>\n")
      socket.end()
    ).listen(843)

这可能是原因吗?

最佳答案

您可能已经猜到了:这是连接错误。

“ECONNRESET” 表示 TCP session 的另一端突然关闭了它的连接端。这很可能是由于一个或多个应用程序协议(protocol)错误造成的。您可以查看 API 服务器日志,看看它是否提示了什么。

但是由于您也在寻找一种方法来检查错误并可能调试问题,因此您应该查看 "How to debug a socket hang up error in NodeJS? ",它发布在 stackoverflow 上,与类似的问题。

Quick and dirty solution for development:

Use longjohn, you get long stack traces that will contain the async operations.

Clean and correct solution: Technically, in node, whenever you emit an 'error' event and no one listens to it, it will throw. To make it not throw, put a listener on it and handle it yourself. That way you can log the error with more information.

To have one listener for a group of calls you can use domains and also catch other errors on runtime. Make sure each async operation related to http(Server/Client) is in different domain context comparing to the other parts of the code, the domain will automatically listen to the error events and will propagate it to it's own handler. So you only listen to that handler and get the error data. You also get more information for free.

编辑 (2013-07-22)

正如我上面写的:

"ECONNRESET" means the other side of the TCP conversation abruptly closed its end of the connection. This is most probably due to one or more application protocol errors. You could look at the API server logs to see if it complains about something.

也可能是这种情况:在随机时间,另一端过载并因此简单地终止连接。如果是这种情况,则取决于您要连接的确切内容……

但有一件事是肯定的:您的 TCP 连接上确实存在读取错误,这会导致异常。您可以通过查看您在编辑中发布的错误代码来确认这一点。

关于node.js - 如何在 Node.js 中调试错误 ECONNRESET?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17245881/

相关文章:

tcp - 谁首先在客户端-服务器连接中设置 tcp FIN 标志

node.js - Firebase云功能日志 'Error: incorrect function response. Function invocation was interrupted.'

javascript - 在 swagger 文档中实现 void

python - 在 Python 中通过套接字发送文件

c++ - 无法接收 UDP 广播消息

tcp - 是什么导致打开这么多 TIME_WAIT 连接?

java - 从 Windows Azure 服务总线获取可用的 TCP 端口

node.js - 生成 mongoinsert

string - Node.js 无法解码字符串..字符乱码(问号)

c# - 从套接字读取数据,发送响应并关闭