Node.js中的HTTP keep-alive

14

我正在尝试在 node.js 中设置 HTTP 客户端以保持基础连接开放 (keep-alive),但似乎其行为与文档不符 (http://nodejs.org/api/http.html#http_class_http_agent)。

我正在创建一个新的 HTTP 代理,将 maxSockets 属性设置为 1,并每秒请求一个 URL(例如 http://www.twilio.com/)。

看来每次请求时套接字都会关闭并创建一个新的套接字。我已经在 Ubuntu 14.04 下测试了 node.js 0.10.25 和 0.10.36。

有人能够使 keep alive 生效吗?

以下是代码:

var http = require("http");

var agent = new http.Agent();
agent.maxSockets = 1;

var sockets = [];

function request(hostname, path, callback) {
    var options = {
        hostname: hostname,
        path: path, 
        agent: agent, 
        headers: {"Connection": "keep-alive"}
    };
    var req = http.get(options, function(res) {
        res.setEncoding('utf8');
        var body = "";
        res.on('data', function (chunk) {
            body += chunk;
        });
        res.on('end', function () {
            callback(null, res, body);
        });
    });
    req.on('error', function(e) {
        return callback(error);
    });
    req.on("socket", function (socket) {
        if (sockets.indexOf(socket) === -1) {
            console.log("new socket created");
            sockets.push(socket);
            socket.on("close", function() {
                console.log("socket has been closed");
            });
        }
    });
}

function run() {
    request('www.twilio.com', '/', function (error, res, body) {
        setTimeout(run, 1000);
    });
}

run();

在你的 http.get() 回调函数中,console.dir(res.headers.connection) 显示什么? - mscdex
我已经检查过了,主机在响应中返回"Connection: keep-alive"头部,表明它确实接受保持连接打开。 - quentinadam
3个回答

14

如果我没记错,连接池是在0.12中实现的。

因此,如果你想在0.12之前拥有连接池,你可以简单地使用 request 模块:

var request = require('request')
request.get('www.twilio.com', {forever: true}, function (err, res, body) {});
如果您正在使用Node 0.12+并希望直接使用HTTP核心模块,则可以使用以下内容初始化代理:
var agent = new http.Agent({
  keepAlive: true,
  maxSockets: 1,
  keepAliveMsecs: 3000
})

注意keepAlive: true属性,它是保持套接字开启所必需的

您也可以向请求模块传递代理,同样只在0.12+上有效,否则默认为内部池实现。


显然,在我发布这篇文章的时候,Node.js 的最新稳定版本是0.10,而我链接的文档也是0.10的文档。感谢您的回答,我会在有机会的时候尝试一下(与此同时,我已经实现了一个解决方法)。 - quentinadam
我甚至没有注意到帖子的日期。无论如何,我的答案仍然是有效的。 - simo

0

我猜它应该可以在node 0.12+上运行。您可能还想使用不同的代理来实现此目的。例如keep-alive-agent可以做到您想要的:

var KeepAliveAgent = require('keep-alive-agent'),
    agent = new KeepAliveAgent();

0

以下内容适用于我在使用npm模块keepaliveagent的Meteor中

var agent = new KeepAliveAgent({ maxSockets: 1 });

var options = {
  agent:agent,
  headers: {"Connection":"Keep-Alive"}
}

try {
  var client = Soap.createClient(url);

  var result = client.myfirstfunction(args,options);

//process result
  result = client.mysecondfunction(args,options);

}

这两个方法调用都在一个套接字连接中返回数据。您需要在每个方法调用中传递选项。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接