HTTP 协议(上下文介绍和多断点续传原理)

HTTP 请求和响应都有一些表示 上下文 的常用头部,所谓 上下文 指的就是某个请求(或响应)从哪里来,或者说某个请求(或响应)对后续请求(或响应)产生哪些影响,后面从 HTTP 协议的角度分析大文件(大的包体)如何做到 断点续传 的,下载大文件(大的包体)的时候是如何做到 多线程 并发下载的。

1.请求的上下文 User-Agent

User-Agent 用于指明客户端的用户类型信息,服务器可以根据此类型信息做出对应响应,下面给出基于 ABNF 描述的 User-Agent 格式:

User-Agent = product*(RWS(product/comment))
  product = token ["/" product-version]
  RWS = 1*(SP/HTAB)

2.User-Agent 示例

2.1 firefox 浏览器中的 User-Agent
User-Agent:Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:83.0) Gecko/20100101 Firefox/83.0

如下图所示:

Tips:Mozilla/5.0 表示浏览器兼容 Mozilla/5.0Windows NT 10.0; Win64; x64; rv:83.0表示的就是操作系统的版本信息,Gecko/20100101firefox 浏览器的渲染引擎,Firefox/83.0 是浏览器的发布版本号。
2.2 chrome 浏览器中的 User-Agent
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.198 Safari/537.36

如下图所示:

Tips:Mozilla/5.0 表示浏览器兼容 Mozilla/5.0Windows NT 10.0; Win64; x64表示的就是操作系统的版本信息,GAppleWebKit/537.36 (KHTML, like Gecko) 表示浏览器的渲染引擎,Chrome/86.0.4240.198Safari/537.36 都是表示浏览器的发布版本号。

2.请求上下文 Referer

2.1 Referer 头部格式

浏览器会对来自某一页面的请求自动添加 Referer 头部信息,格式如下:

Referer = absolute-URI / partial-URI

如下图所示:

Tips:图中表示从 www.baidu.com 跳转过去的,防盗链的时候可以用到。
2.2 Referer 不被添加到头部的场景
  • 来源页面采用的协议是表示本地文件的 filedataURI
  • 当前请求页面采用的是 http 协议,而来源页面采用的是 https 协议。
2.3 Referer 常见作用
  • 服务器统计分析
  • 缓存优化
  • 防盗链

3.请求上下文 From

From 主要用于网络爬虫,告诉服务器如何通过邮件联系到爬虫负责人,格式如下:

From = mailbox
Tips:例如:From:webmaster@example.org

4.响应的上下文 Server

指明了服务器中所用的软件信息,用于帮助客户端定位问题或者同级数据,格式如下:

Server = product*(RWS(product/comment))
  product = token ["/" product-version]

如下图所示:

5.响应上下文 Allow、Accept-Ranges

5.1 Allow

告诉客户端,服务器上 URI 对应的资源允许哪些方法的执行,格式如下:

Allow = #method
Tips:例如:GET、HEAD、PUT
5.2 Accept-Ranges

告诉客户端服务器上该资源是否允许 range 请求,格式如下:

Accept-Ranges = accepttable-ranges
Tips:例如:Accept-Ranges:bytes、Accept-Ranges:none

6.上下文 Connection

Connection: keep-alive 表示长连接,当事务完成后,不会关闭网络连接,Connection: close 表示短连接,客户端或服务器端想要关闭网络连接,如下图所示:

7.多线程、断点续传、随机点播步骤

  • 1.客户端明确任务:从哪里开始下载,本地是否已经有部分文件,文件已下载部分是否在服务器端发生改变,使用几个线程并发下载。
  • 2.下载文件的指定部分内容。
  • 3.下载完毕后拼装成统一的文件。

8.HTTP Range 规范(RFC 7233)

  • 允许服务器基于客户端的请求只发送响应包体的一部分给到客户端,而客户端自动将多个片断的包体组合成完整的更大的包体,支持断点续传,支持多线程下载,支持视频播放器实时拖动。
  • 服务器通过 Accept-Range 头部表示是否支持 Rang 请求,格式如Accept-Ranges = acceptable-ranges,例如 Accept-Ranges:bytes表示支持,Accept-Ranges:none不表示不支持。

9. Range 请求范围的单位

9.1 Range 头部格式

基于字节,假设包体总长度为 500Range 头部格式如下:

#第一个 100 字节
bytes=0-99
#第二个 100 字节
bytes=100-199
bytes=100-120,121-199
bytes=100-155,156-199
#最后一个 100 字节
bytes=-100
bytes=100-
#仅仅只传第一个和最后一个字节
bytes=0-0,-1
Tips:通过 Range 头部传递请求范围,如:Range:bytes=0-99
9.2 curl 模拟 Range
#全部内容:abcdefghijklmnopqrstuvwxyz1234567890,下面是只截取第 21 字节到最后

curl http://singwa666.com/text.txt -H 'Range:bytes=20-30'
9.3 wireshark 抓取请求报文

如下图所示:

wireshark 抓包中的 HTTP 请求数据如下:

Tips:其中 Range:bytes=20-30\r\n 表示告诉服务器只返回第 21 字节至 第 31 字节的内容。
9.4 wireshark 抓取请求报文

wireshark 抓包中的 HTTP 响应数据如下:

Tips:其中 ETag: "5fd06ef3-24"\r\n 表示该请求内容的 指纹。
9.5 Range 条件请求模拟断点续传

http://singwa666.com/text.txt 中存放的是 abcdefghijklmnopqrstuvwxyz123456789036 字节的内容。
步骤1: 请求第 0-5 字节
若客户端已经得到了 Range 响应的一部分,并想在这部分响应未过期的情况下,获取其他部分响应就可以使用 If-Unmodified-SinceIf-Match头部,请求 0-5 字节命令如下:

curl http://singwa666.com/text.txt -H 'Range:bytes=0-5' -I

如下图所示:

Tips:-I 表示显示服务器响应内容,ETag: "5fd06ef3-24" 表示响应内容的指纹。

步骤2:请求 6-10 字节,Etag 指纹匹配场景
使用 If-Match 判断步骤1指纹内容,使用匹配的指纹:

curl http://singwa666.com/text.txt -H 'Range:bytes=6-10' -H 'If-Match: "5fd06ef3-24"'

如下图所示:

Tips:此时能得到正确的 6-10 字节响应,客户端可以把获取的内容和第一段获取的内容合并成完整的内容。

步骤2:请求 6-10 字节,Etag 指纹不匹配场景
使用 If-Match 判断步骤1指纹内容,使用不匹配的指纹:

curl http://singwa666.com/text.txt -H 'Range:bytes=6-10' -H 'If-Match "aaaaaaa-24"'

如下图所示:

Tips:此时 HTTP 状态码 412,表示提示客户端需要重新去获取第一段内容才能合成完整的内容。
9.6 Range 相关的服务器响应
  • 206 Partial Content:格式如下:
#Content-Range 头部:显示当前片段包体在完整包中的位置
Content-Range = byte-content-range / other-content-range
   byte-range-resp = byte-range "/" (complete-length / "*")
      complete-length = 1*DIGIT
#完整资源的大小,如果未知则用 `*` 替代

如下图所示:

Tips:Content-Range: bytes 0-5/36\r\n 表示只响应返回了全部 36 字节中的 0-5 字节内容。
  • 断点续传应用场景,如下图所示表示服务器响应的 Range 的数据:

Tips:其中 Content-Range: bytes 9240576-35698347/35698348 表示响应内容 9240576-35698347 字节内容,全部 35698348 字节,ETag 表示内容指纹 E046100C5DF23585361797FD9647BC74-2
  • 视频断点请求 Range 数据如下:

Tips:其中 Range: bytes=9240576-35698347 表示请求第 924057635698347 字节的内容。
  • 416 Range Not Satisfiable
curl http://singwa666.com/text.txt -H 'Range:bytes=50-60' -H 'If-Match: "5fd06ef3-24"'

如下图所示:

  • 200 OK:若服务器不支持 Range 请求时,则会返回 200 完整的响应包体。
Tips:可以使用 Range:0-10,20-30 使用多范围请求。

扫码关注爱因诗贤
在这里插入图片描述


爱因诗贤
54 声望9 粉丝