“超文本传输协议”
HTTP 是一个在计算机世界里专门在两点之间传输文字、图片、音频、视频等超文本数据的约定和规范。 通常跑在 TCP/IP 协议栈上,依靠 IP 协议实现寻址和路由、TCP 协议实现可靠数据传输、DNS 协议实现域名查找、SSL/TLS 协议实现安全通信。
HTTP 特点
- 灵活可扩展:报文各个组成部分可以定制
- 可靠传输:基于 TCP/IP 协议
- 应用层协议:能够传输任意数据
- 请求 - 应答:请求方主动发起请求,应答方被动回复请求
- 无状态:每个请求都是互相独立、毫无关联的,协议不要求客户端或服务器记录请求相关的信息
HTTP 报文
HTTP 协议的核心内容:传输的报文内容
报文结构
- 起始行(start line):描述请求或响应的基本信息
- 头部字段集合(header):使用 key-value 形式说明报文
- 消息正文(entity):实际传输的数据
请求行
描述客户端想要如何操作服务端的资源
GET / HTTP/1.1
HTTP/1.1 200 OK
请求方法
HEAD:服务器不会放回请求的实体数据,只会返回响应头
POST:新建
PUT:修改
OPTIONS:复杂请求发送之前,一般会需要通过这个方法发送一个预检请求,通过响应头来判断是否可以跨域
响应状态码(status code)
表示服务器对请求的处理结果
- 1××:提示信息,表示目前是协议处理的中间状态,还需要后续的操作;
- 2××:成功,报文已经收到并被正确处理;
- 3××:重定向,资源位置发生变动,需要客户端重新发送请求;
- 4××:客户端错误,请求报文有误,服务器无法处理;
- 5××:服务器错误,服务器在处理请求时内部发生了错误。
常用状态码
// Location 标记服务器要求重定向的 URI
Location:/index.html
URI
统一资源标识符(Uniform Resource Identifier)
基本组成
- scheme:表示资源应该用哪种协议来访问
- authority:表示资源所在的主机名
- host:主机名
- port:端口号
- path:标记资源所在位置(路径)
?query:表示对资源附加的额外要求(”key=value”的字符串)
http://www.chrono.com:8080/11-1?uid=1234&name=mario&referer=xxx
完整格式
user:passwd@:身份信息,表示登录主机时的用户名和密码(现在不使用)
fragment:定位的资源内部的”锚点“,只存在客户端不会发送给服务端
HTTP 传输大文件
- 数据压缩
- 分块传输
- 范围请求
- 多段数据
数据压缩
Accept-Encoding: gzip, deflate, br(三种压缩算法)
Content-Encoding: gzip
分块传输
分块传输的编码规则:Transfer-Encoding:chunked
- 每个分块:长度头 + 数据块
范围请求(range requests)
允许客户端在请求头里使用专用字段来表示只获取文件的一部分
// 请求头
bytes=x-y (x 和 y 是以字节为单位的数据范围)
Range: bytes=0-31
// 服务端
Content-Length: 32
Accept-Ranges: bytes
Content-Range: bytes 0-31/96
多段下载、断点续传
- 先通过 HEAD 获取服务端是否支持范围请求、获取文件大小
- 开 N 个线程,每个线程使用 Range 字段划分出各自负责下载的片段,发送请求传输数据
- 下载中断时,通过下载记录,用 Range 请求剩余部分
多段数据
一次性获取多个片段数据 “multipart/byteranges”,表示报文的 body 是由多段字节序列组成的 “boundary=xxx”给出段之间的分隔标记。
// 请求头
GET /16-2 HTTP/1.1
Host: www.chrono.com
Range: bytes=0-9, 20-29
// 响应头
HTTP/1.1 206 Partial Content
Content-Type: multipart/byteranges; boundary=00000000001
Content-Length: 189
Connection: keep-alive
Accept-Ranges: bytes
--00000000001
Content-Type: text/plain
Content-Range: bytes 0-9/96
// this is
--00000000001
Content-Type: text/plain
Content-Range: bytes 20-29/96
ext json d
--00000000001--
HTTP 的连接管理
Connection:keep-alive/close
队头阻塞
由 HTTP 的“请求 - 应答”模型导致 因为 HTTP 规定报文必须是“一发一收”,这就形成了一个先进先出的“串行”队列。队列里的请求没有轻重缓急的优先级,只有入队的先后顺序,排在最前面的请求被最优先处理。
性能优化
- 负载均衡:把外部的流量合理地分散到多台源服务器,提高系统的整体资源利用率和性能。
- 健康检查:使用“心跳”等机制监控后端服务器,发现有故障就及时“踢出”集群,保证服务高可用
- 安全防护:保护被代理的后端服务器,限制 IP 地址或流量,抵御网络攻击和过载
- 加密卸载:对外网使用 SSL/TLS 加密通信认证,而在安全的内网不加密,消除加解密成本
- 数据过滤:拦截上下行的数据,任意指定策略修改请求或响应
- 内容缓存:暂存、复用服务器响应