http协议从1.1开始支持获取文件的部分内容,这为并行下载以及断点续传提供了技术支持。
如对于一个多线程下载工具,服务器端把文件分割成多个部分,比如4个部分(如文件大小为403个 byte,那么可能的分割方式可以为:0-99 (前100个字节),100-199(第二个100字节),200-299(第三个100字节),300-402(最后103个字节)),然后对应4个线程,客户端每个线程负责下载一个部分。现在的问题是线程3发送一个什么样的请求报文,才能够保证 只请求文件的200-299字节,而不会干扰其他线程的任务。
再有如果一个线程进行上传/下载过程中碰到网络故障,我们希望可以从已经上传/下载的部分开始继续上传/下载未完成的部分,而没有必要从头开始上传/下载??梢越谑∈奔洌屯缱试?。
HTTP1.1中上述问题的解决方法是通过在请求/响应的Header里设置参数实现的,客户端发请求时对应的是Range,服务器端响应时对应的是Accept-Ranges、Content-Range。
如果Server支持分段下载,那么在客户端请求资源之前,首先要告诉客户端,它支持Range,之后客户端才可能发起带Range的请求。如在如下一个页面中下载某个资源的时候,
server 主动告诉 client “Accept-Ranges: bytes”。
Server通过请求头中的Range:bytes=xxx-xxx(xxx-xxx表示字节范围,字节数从0开始计数)来判断是否是做Range请求,如果这个值存在而且有效,则只发回请求的那部分文件内容,响应的状态码变成206,表示Partial Content,并设置Content-Range。如果无效,则返回416状态码,表明Request Range Not Satisfiable,如果不包含Range的请求头,则继续通过常规的方式响应。
如用curl工具模拟在该页面中下载某一资源(http://swf.ishare.down.sina.com.cn/7edhKNThu1.jpg)的一次分段请求,请求时把respons的header给dump到一个文件里:
[root@localhost~]# curl -D "rsp.txt" -H "Range:bytes=0-184697""http://swf.ishare.down.sina.com.cn/7edhKNThu1.jpg?ssig=tpNfKjRHRO&Expires=1567278916&KID=sina,ishare">> test.png
? % Total???% Received % Xferd? AverageSpeed?? Time??? Time????Time? Current
???????????????????????????????? Dload? Upload??Total?? Spent??? Left?Speed
100? 180k?100? 180k??? 0????0?? 939k????? 0 --:--:-- --:--:-- --:--:--? 939k
[root@localhost~]#
?????? 上述的意思就是将前184698字节的数据下载下来。
现在看一下这个资源片段的大小
[root@localhost~]# ll | grep test.jpg
-rw-r--r--? 1 root???root???? 184698 Jul 12 19:15test.jpg
?????? 可以看出本次下载的资源大小为184698字节。
?????? 查看一下响应头,如
[root@localhost~]# cat rsp.txt
HTTP/1.1 206 Partial Content
Date:Fri, 12 Jul 2019 11:15:59 GMT
Content-Type:application/octet-stream
Content-Length: 184698
Connection:keep-alive
Server:nginx/1.6.0 r19071115-afb7a4e
X-RequestId:00a6a1df-1907-1218-5024-782bcb648fb2
X-Requester:SINA0000000000ISHARE
Last-Modified:Mon, 25 Sep 2017 03:30:59 GMT
X-Filesize:9659323
ETag:"d6931115ddb9e82fa7eeddd4c9dfdd94"
x-amz-meta-crc32:C5619893
Cache-Control:max-age=31536000
Access-Control-Allow-Headers:Origin, Content-Type, Accept, Range, Content-Length
Access-Control-Allow-Methods:GET, PUT, POST, DELETE, OPTIONS, HEAD
Access-Control-Max-Age:31536000
Access-Control-Allow-Origin:*
X-Via-CDN:f=cnct,s=PSbjbgddxqe151:14,c=221.122.104.1;f=cnct,s=uzhoudianxin66:3,c=221.122.104.1;f=cnct,s=hxian174:6,c=221.122.104.1
Content-Range: bytes 0-184697/9659323
Age: 1
X-Via:1.1 hxian174:6 (Cdn Cache Server V2.0), 1.1 uzhoudianxin66:3 (Cdn Cache ServerV2.0), 1.1 PSbjbgddxqe151:14 (Cdn Cache Server V2.0)
?
[root@localhost~]#
?????? 正常的情况下,服务器响应状态码为206,表示本次请求处理成功。响应头中的Content-Range: bytes 0-184697/9659323行,斜杠后面的9659323表示文件的大小。