我用express创建一个http服务器。 以下是服务器代码:
router.get('/', function(req, res, next) {
// req.socket.setTimeout(Infinity);
res.writeHead(200, {
'Content-Type': 'text/plain; charset=utf-8', // <- Important headers
'Cache-Control': 'no-cache',
'Connection': 'keep-alive',
});
res.write('hell');
res.write('world');
res.end();
// res.write('\n\n');
// response = res;
});
当我使用netcat来获取网址时。 输出就像这样
GET /sse HTTP/1.1
HTTP/1.1 200 OK
X-Powered-By: Express
Content-Type: text/plain; charset=utf-8
Cache-Control: no-cache
Expires: 0
Connection: keep-alive
Keep-Alive: timeout=5, max=97
Date: Fri, 30 Jun 2017 11:50:00 GMT
Transfer-Encoding: chunked
4
hell
5
world
0
我的问题是为什么每个res.write()之前总有一个数字?然后数字似乎是res.write输出的长度。
如何删除号码?
答案 0 :(得分:3)
这是分块编码的工作原理。您不必预先声明要发送多少字节,而是每个块前面加上它具有的字节数。例如:4表示"hell"
,5表示"world"
,最后0表示“不再发送字节”。
您可以看到存在分块编码头:
Transfer-Encoding: chunked
现在,要直接回答您的问题,要删除您必须关闭分块编码的数字。为此,您必须将Content-length标头设置为您将在响应正文中发送的字节数。
例如:
app.get('/', function(req, res, next) {
res.writeHead(200, {
'Content-Type': 'text/plain; charset=utf-8',
'Cache-Control': 'no-cache',
'Connection': 'keep-alive',
'Content-length': 9, // <<<--- NOTE HERE
});
res.write('hell');
res.write('world');
res.end();
});
(当然在实际代码中你必须要么计算响应的长度,要么建立一个字符串或缓冲区,并在设置Content-length标题之前得到它的长度。)
但请注意,如果您使用curl或任何其他HTTP客户端,那么它将为您“删除”这些数字。只是用netcat你意外地看到了分块编码的底层实现细节,但所有真正的HTTP客户端都可以正常处理。
通常在HTTP中,你在头文件中声明整个响应的长度,然后发送正文 - 一个部分,多个块,无论如何 - 但它必须与你声明的长度相同。这意味着在知道要发送的所有内容的长度之前,无法开始发送数据。使用分块编码,它足以声明您发送的每个块的长度,但您不必知道整个响应的长度 - 这甚至可能是无限的,这取决于您。它允许您在发送任何内容后立即开始发送,这非常有用。