5

我正在用 Node.js + Express 2 编写代理。代理应该:

  1. 解密 POST 有效载荷并根据结果向服务器发出 HTTP 请求;
  2. 加密来自服务器的回复并将其发送回客户端。

与加密相关的部分工作正常。我面临的问题是超时。代理应在 15 秒内处理请求。实际上,它们中的大多数都在 500 毫秒以下。

当我增加并行请求的数量时出现问题。大多数请求都可以正常完成,但有些请求在 15 秒 + 几毫秒后失败。ab -n5000 -c300工作正常,但在 500 并发时,某些超时请求会失败。

我只能推测,但似乎问题是回调执行的顺序。是否有可能首先出现的请求会一直挂起,直到ETIMEDOUT因为节点关注最新的请求,这些请求仍在 500 毫秒内及时处理。

PS:远程服务器没有问题。我正在使用请求与它进行交互。

更新

一些代码的工作方式:

function queryRemote(req, res) {
  var options = {};  // built based on req object (URI, body, authorization, etc.)
  request(options, function(err, httpResponse, body) {
    return err ? send500(req, res)
               : res.end(encrypt(body));
  });
}

app.use(myBodyParser);  // reads hex string in payload
                        // and calls next() on 'end' event

app.post('/', [checkHeaders,   // check Content-Type and Authorization headers
               authUser,       // query DB and call next()
               parseRequest],  // decrypt payload, parse JSON, call next()
         function(req, res) {
  req.socket.setTimeout(TIMEOUT);
  queryRemote(req, res);
});

我的问题如下:当ab发布 20 个 POST 到 时/,快速路由处理程序会被调用数千次。这并不总是发生,有时会及时处理 20 个请求,只有 20 个请求。

当然,ab不是问题。我 100% 确定只有 20 个请求由ab. 但是路由处理程序被多次调用。

我找不到这种行为的原因,有什么建议吗?

4

2 回答 2

2

超时是由于使用http.globalAgent默认情况下最多可以处理5 个并发请求而导致的host:port(在我的情况下这还不够)。

成千上万的请求(而不是几十个)是由ab(Wireshark 在 OS X 下批准的事实;我无法在 Parallels 内的 Ubuntu 下重现这一点)发送的。

于 2012-12-05T15:15:44.707 回答
1

您可以查看node-http-proxy模块以及它如何处理连接。确保您不缓冲任何数据,并且一切都通过流式处理。您应该尝试查看这些长请求花费的时间在哪里。conosle.time尝试使用and检测部分代码,console.timeEnd看看哪里花费的时间最多。如果时间主要花在 javascript 上,您应该尝试对其进行分析。基本上,您可以通过在节点命令中添加 --prof 选项来使用 v8 分析器。这会生成一个v8.log,并且可以通过node-source-dir/deps/v8/tools中的 v8 工具进行处理。仅当您通过scons (scons d8) 安装了 d8 shell 时它才有效。你可以看看这篇文章帮助您进一步完成这项工作。

您还可以使用node-webkit-agent,它使用 webkit 开发人员工具来显示分析器结果。你也可以看看我的叉子加点糖。

如果这不起作用,您可以尝试使用 dtrace 进行分析(仅适用于 SmartOS 等基于 illumos 的系统)。

于 2012-11-11T03:18:37.730 回答