浏览器和wget加载JPEG不同?

时间:2011-03-31 23:51:02

标签: python image facebook cdn

我很难过这个。尝试在浏览器中加载此图像,然后将其保存到硬盘中。

http://profile.ak.fbcdn.net/hprofile-ak-snc4/41674_660962816_995_n.jpg

这是一个11377字节的有效JPEG文件。

现在尝试使用wgetcurl下载它。仅显示11252个字节,并且图像的右下部分缺失。

是什么给出了?

2 个答案:

答案 0 :(得分:13)

这里......

进行数据包转储后,我看到Facebook将相同的 Content-Length返回到Safari,就像它卷曲一样,而且内容长度是不正确的 11252:

GET /hprofile-ak-snc4/41674_660962816_995_n.jpg HTTP/1.1
User-Agent: curl/7.19.7 (universal-apple-darwin10.0) libcurl/7.19.7 OpenSSL/0.9.8l zlib/1.2.3
Host: profile.ak.fbcdn.net
Accept: */*

HTTP/1.1 200 OK
Content-Type: image/jpeg
... snip ....
Content-Length: 11252

使用Safari:

GET /hprofile-ak-snc4/41674_660962816_995_n.jpg HTTP/1.1
Host: profile.ak.fbcdn.net
User-Agent: Mozilla/5.0 (Macintosh; U; Intel Mac OS X 10_6_6; en-us) AppleWebKit/533.20.25 (KHTML, like Gecko) Version/5.0.4 Safari/533.20.27
... snip ...

HTTP/1.1 200 OK
Content-Type: image/jpeg
... snip ...
Content-Length: 11252

所以我猜猜Facebook发送的内容长度不正确。为了测试这个,我将使用netcat:

$ cat  headers
GET /hprofile-ak-snc4/41674_660962816_995_n.jpg HTTP/1.0
Host: profile.ak.fbcdn.net
Accept: */*

EOF
$ nc -vvv profile.ak.fbcdn.net 80  output
Warning: Inverse name lookup failed for `142.231.1.174'
Notice: Real hostname for profile.ak.fbcdn.net [142.231.1.165] is a142-231-1-165.deploy.akamaitechnologies.com
profile.ak.fbcdn.net [142.231.1.174] 80 (http) open
Total received bytes: 12k (11639)
Total sent bytes: 97
$ head output
HTTP/1.0 200 OK
Content-Type: image/jpeg
... snip ...
Content-Length: 11252

(请注意,我使用了 HTTP / 1.0 ,因此Facebook服务器不会尝试保持连接打开)

使用文本编辑器删除前10行ouput,然后将其保存为output.jpg,我已经获得了完整的图像。

因此,这确认了Facebook正在发送一个不正确的Content-Length标题(并且图像正在被切断,因为curl正在关注内容长度而netcat不是)。

进一步挖掘,似乎Aleski是正确的 - 当图像被发送gzip压缩时Content-Length是正确的。为了确认这一点,我将Accept-Encoding: gzip添加到我的headers文件中。 Facebook正确地发送了一个gzip的响应,这是预期的长度,解压缩会产生正确的图像。

tl; dr :如果Content-Length不是Content-Encoding,则Facebook的gzip不正确。

答案 1 :(得分:4)

服务器似乎有问题。当我测试它时,firefox和wget之间的区别在于firefox表示它接受gzip或deflate -compressed答案的请求,而wget没有。

服务器对firefox的响应是11252字节的压缩数据,而对wget的响应是11377字节的未压缩数据。然而,它发送的内容长度为11252(正如David所说)。

换句话说,即使在发送未压缩的数据时,似乎服务器正在缓存压缩版本并错误地发送压缩大小。您获得了所有数据,但由于服务器通告的数据较少,因此wget(以及其他要求未压缩数据的软件)会丢弃“额外”数据。