HTTP状态码206和416
HTTP 2xx范围内的状态码表明了:"客户端发送的请求已经被服务器接受并且被成功处理了".
TTP/1.1 200 OK是HTTP请求成功后的标准响应
HTTP/1.1 206状态码表示的是:"客户端通过发送范围请求头Range抓取到了资源的部分数据",一般用来
解决大文件下载问题
解决CDN和原始HTTP服务器问题
使用工具例如lftp,wget,telnet测试断电续传
1、如何判断远程服务器是否支持HTTP 206
其中有两个我们比较关注的请求头:
Accept-Ranges: bytes - 该响应头表明服务器支持Range请求,以及服务器所支持的单位是字节(这也是唯一可用的单位).我们还能知道:服务器支持断点续传,以及支持同时下载文件的多个部分,也就是说下载工具可以利用范围请求加速下载该文件.Accept-Ranges: none 响应头表示服务器不支持范围请求.
Content-Length: 913 Content-Length响应头表明了响应实体的大小,也就是真实的图片文件的大小是913字节 .
2、如何发送一个range请求头
现在,你知道了该图片所在的服务器支持范围请求,你需要发送一个包含Range请求头的GET请求:
Range: bytes=0-1024
完整的请求数据应该是这样的.首先第一行是:
GET /images/misc/static/2012/11/ifdata-welcome-0.png HTTP/1.1
然后需要发送Host请求头来指定请求资源所在的主机和端口号:
最后是要发送的Range请求头,指定了你想要的字节范围:
Range: bytes=0-1024
a、使用telnet命令
telnet命令允许你使用Telnet协议来与远程主机(服务器)进行通信.所有的类Unix操作系统以及MS-Windows都包含有Telnet客户端.启动Telnet客户端并进入Telnet提示符,要执行命令:
输出结果为:
b、使用curl命令
curl命令是一个和远程服务器交换数据的工具.它支持HTTP/FTPSFTP/FILE协议上的范围请求,在下例中,使用两段范围来请求远程文件ifdata-welcome-0.png,然后使用cat命令将两段数据合并成完整文件:
第二部分以及合并
还可以使用-r选项(可以同时添加-v选项查看请求头和响应头):
3、如何开启Accept-Ranges响应头?
大部分web服务器都原生支持字节范围请求. Apache 2.x用户可以在httpd.conf中尝试mod_headers:
1 Header set Accept-Ranges bytes
Lighttpd用户尝试在lighttpd.conf中进行下面的配置:
## enabled for all file types ##
server.range-requests = "enable"
## But, disable it for pdf files ##
$HTTP["url"] =~ "\.pdf$" {
server.range-requests = "disable"
}
4、HTTP 416错误与断点续传
先看下HTTP 416错误代表什么吧?
所请求的范围无法满足 (Requested Range not satisfiable)
看了不明觉厉,因为从没遇见过。
##探索 问了下客户端的同学,发现下载使用的是HttpURLConnection,于是Google一下,得到一些关键信息:
HTTP response code: 416是由于读取文件时设置的Range有误造成的,具体的说就是下面这行代码有误:
httpConnection.setRequestProperty("RANGE", "bytes=1024-");
这个RANGE显然不能超出文件的size而客户端设置的RANGE为文件大小。
试想,文件存在远程服务器上,如何知道文件大小?
至少要发起两次请求。第一次请求,不需要下载整个文件,只需要获得Response的Content-Length大小;第二次请求,将Content-Length值写进RANGE,实现下载。
造成返回码416的原因,是设置的Range有误。解决办法也很简单,将第一次请求时的Range去掉。
//删掉之后,整个世界都清净了!
conn.setRequestProperty("Range", "bytes=" + startPosition);// startPosition=0
讨论 下载地址是CDN地址,莫非CDN不支持断点续传?
恰好相反,416正是支持断点续传的标志。服务器得到一个Range之后,需要对它的取值进行检验,包括:
开始位置非负
结束位置需要大于开始位置
开始位置需要小于文件长度减一 (因为这里的位置索引是从0开始的)
若结束位置大于文件长度减一,则需要把它的值设置为文件长度减一