hi, 各位
server {
listen 8707;
server_name _;
location / {
content_by_lua '
ngx.header["Transfer-Encoding"] = "chunked"
ngx.header["Connection"] = "keep-alive"
ngx.say("hello world")
';
}
}
在调用 ngx.header 设置 Transfer-Encoding 和 Connection 头部时, 为何最终输出会重复包含 2 次?
$ curl http://127.0.0.1:8707 -I
HTTP/1.1 200 OK
Server: nginx/1.2.6
Date: Mon, 20 May 2013 07:08:14 GMT
Content-Type: text/plain
Connection: keep-alive
Transfer-Encoding: chunked
Connection: keep-alive
$ curl http://127.0.0.1:8707 -v
< HTTP/1.1 200 OK
< Server: nginx/1.2.6
< Date: Mon, 20 May 2013 07:07:36 GMT
< Content-Type: text/plain
< Transfer-Encoding: chunked
< Connection: keep-alive
< Transfer-Encoding: chunked
< Connection: keep-alive
<
hello world
如上所示, 其中 curl HEAD 请求, Transfer-Encoding 并没有重复, 怀疑是否是 Nginx body filter 过程中加上去的?
并且由于 Transfer-Encoding: chunked 头部的重复, 造成了 Python httplib 标准库读取 chunked body 数据时底层 socket.read 操作似乎会被阻塞一会儿, 并且输出的 body 内容包含了 chunked 数据块的 16 进制标识.
当然, 这个是题外话了, Python 的 httplib 在处理重复的 Transfer-Encoding: chunked 头似乎也有点问题. :-)
#! /usr/bin/env python
# -*- coding: utf-8 -*-
import httplib
connection = httplib.HTTPConnection("127.0.0.1:8707")
connection.request("GET", "/")
r = connection.getresponse()
print r.status, r.reason
print r.read()
$ time python test.py
200 OK
c
hello world
0
real 1m5.077s
user 0m0.025s
sys 0m0.015s
从 wireshark 捕获 Nginx <-> Python Client 之间的数据来看, 似乎也没有看到 body 体被 chunked 两次的情况
0040 01 40 c2 0c 48 54 54 50 2f 31 2e 31 20 32 30 30 .@..HTTP /1.1 200
0050 20 4f 4b 0d 0a 53 65 72 76 65 72 3a 20 6e 67 69 OK..Ser ver: ngi
0060 6e 78 2f 31 2e 32 2e 36 0d 0a 44 61 74 65 3a 20 nx/1.2.6 ..Date:
0070 4d 6f 6e 2c 20 32 30 20 4d 61 79 20 32 30 31 33 Mon, 20 May 2013
0080 20 30 37 3a 32 36 3a 35 39 20 47 4d 54 0d 0a 43 07:26:5 9 GMT..C
0090 6f 6e 74 65 6e 74 2d 54 79 70 65 3a 20 74 65 78 ontent-T ype: tex
00a0 74 2f 70 6c 61 69 6e 0d 0a 54 72 61 6e 73 66 65 t/plain. .Transfe
00b0 72 2d 45 6e 63 6f 64 69 6e 67 3a 20 63 68 75 6e r-Encodi ng: chun
00c0 6b 65 64 0d 0a 43 6f 6e 6e 65 63 74 69 6f 6e 3a ked..Con nection:
00d0 20 6b 65 65 70 2d 61 6c 69 76 65 0d 0a 54 72 61 keep-al ive..Tra
00e0 6e 73 66 65 72 2d 45 6e 63 6f 64 69 6e 67 3a 20 nsfer-En coding:
00f0 63 68 75 6e 6b 65 64 0d 0a 43 6f 6e 6e 65 63 74 chunked. .Connect
0100 69 6f 6e 3a 20 6b 65 65 70 2d 61 6c 69 76 65 0d ion: kee p-alive.
0110 0a 0d 0a 63 0d 0a 68 65 6c 6c 6f 20 77 6f 72 6c ...c..he llo worl
0120 64 0a 0d 0a 30 0d 0a 0d 0a d...0... .