最近快速看完了《图解HTTP》一书,写篇文章总结一下,更详细的内容还是建议大家去看一下这本书
了解Web及网络基础
通过在浏览器输入一个URL,敲入回车便可以完成一次请求。此时,浏览器从服务器获取到文件资源信息,然后在我们的浏览器中显示请求到的页面。负责发送请求的一端我们称之客户端
,负责响应请求的一端我们称之为服务端
。客户端和服务端的通信建立在HTTP协议上。
不同的硬件和操作系统,如果它们之间要实现通信的话,需要指定一种准则,这种准则我们称之为协议
。我们现在所使用的网络都是在TCP/IP协议族的基础上运作的。通过下图简单了解一下
与HTTP相关的很重要的三个协议:IP
、TCP
、DNS
-
IP:负责传输数据,把数据包发送到对方。这其中会用到
IP地址
和Mac地址
。IP地址随着连接的网络不同也会不一样,比如你在家连的网络和你在公司连的网络的IP地址是不一样的。然而对于Mac地址来说,它是唯一的,每一台设备的Mac地址是不会变的,除非你更换你的网卡(即网络适配器),或者你的设备有多个网卡(于此同时你的设备也就有了多个Mac地址)。一般情况下,一台设备都只有一个网卡。因为IP协议的通信需要Mac地址来寻址目标,所以会用到ARP(地址解析协议,Address Resolution Protocol),查出IP地址所对应的Mac地址 -
TCP:对于TCP,它提供一种可靠的字节流服务,它会确认数据最终是否送到了对方的手中。然而在传输之前,会进行一个三次握手的过程,使用TCP的标志
SYN(synchronize)
和ACK(ackowledgement)
。
- DNS:负责将域名解析为IP地址,或者将IP地址解析为域名。在浏览器输入域名后,客户端会先从DNS服务器上查询对应的IP地址,之后才向目标地址发送HTTP请求
URI 和 URL(在看本书之前,我是不知道URI的,只知道URL🤣)
- URI(Uniform Resource Identifier):统一资源标识符。意思就是由某个协议方案表示的资源的定位标识符。用字符串标识某一互联网资源
- URL(Uniform Resource Locator):统一资源定位符。浏览器上我们输入的网址就是URL。它表示资源的地点(互联网上所处的位置)
需要说一下的是相对URL
,它是从URI中指定的URL,比如URIhttp://www.baidu.com/book/a.txt
,其中/book/a.txt
就是相对URL
其实可以把URL说成URI,也可以把URI说成URL。但是需明确的是URL是URI的子集。可以参考一下绝对URI
的格式
了解HTTP协议
(1)、在网页上输入网址后,浏览器便会发送一个请求到服务器,服务器在收到请求后,会发送一个响应给服务器。
下图展示了一个请求报文的组成:请求方法、请求URI、协议版本、可选的请求首部字段、内容实体
下图展示了一个响应报文的组成:协议版本、状态码、解释状态码的原因短语、可选的相应首部字段、实体主体
响应报文的组成(截取自书中)(2)、需要知道的是,HTTP协议是不保存状态。也就是说它不保存之前的请求和响应报文的信息。每一次新的请求,都会有对应的新的响应。另外HTTP支持持久连接,通过一次TCP连接,可以持续发送请求,直到断开连接
(3)、了解几个HTTP的请求会使用到的方法
- GET:获取服务器资源、传输实体主体
- PSOT:传输实体主体(GET同样也可以传输实体主体,但一般采用POST)、获取服务器资源
- PUT:类似于FTP的文件上传
- HEAD:获取报文首部
- DELETE:删除文件
- OPTIONS:询问支持的方法
- TRACE:追踪路径(通常不会用到)
- CONNECT:要求用隧道协议连接代理
(4)了解Cookie
了解HTTP报文
HTTP报文分为报文首部和报文主体。它们之间用空行(CR+LF)分割,如下图
HTTP报文结构(截取自书中)请求报文和响应报文结构如下图
请求和响应报文结构图(截图自书中)
对于请求行:其中包含请求的方法、请求的URI以及请求的HTTP版本
对于状态行:其中包含请求结构的状态码、原因短语以及HTTP版本
对于首部字段:分4种。请求、响应、通用、实体首部
需要明确的一个区别是报文主体
和实体主体
- 报文(message):HTTP通信基本单元,由8位组字节流组成,通过HTTP通信传输
- 实体(entity):作为请求和响应的有效载荷数据被传输,其内容由实体首部和实体主体组成
HTTP报文的主体用于传输请求或响应的实体主体,通常情况下它俩是等价的
当我们发送邮件时,可能会添加附件。这个是因为采用了MIME(Multipurpose Internet Mail Extensions,多用途因特网邮件扩展)机制,通过它可以允许邮件处理文本、图片、视频等不同类型数据。对于HTTP协议我们可能在发送报文的时候,在报文主体内包含多种类型的实体。那么相应的我们可以在报文中包含如下字段:
- multipart/form-data:在Web表单文件上传时使用
- multipart/byteranges:状态码206(Partial Content,部分内容)响应报文包含了多个范围的内容时使用
在使用上述多部分对象集合时,需要在首部添加Content-Type
字段
了解HTTP状态码
HTTP状态码可以说明请求的返回结果,以3位数字和原因短语构成。数字中的第一位指定了响应类别,后两位无分类。如下表:
类别 | 原因短语 | |
---|---|---|
1XX | Infomational(信息性状态码) | 接收的请求正在处理 |
2XX | Success(成功状态码) | 请求正常处理完毕 |
3XX | Redirection(重定向状态码) | 需要进行附加操作以完成请求 |
4XX | Client Errot(客户端错误状态码) | 服务器无法处理请求 |
5XX | Server Error(服务器错误状态码) | 服务器处理请求出错 |
在RFC2016中的状态码有好几十种,书中提到有40种,但比较常用的也就14种
- 200 OK:表示客户端的请求被服务器正常处理
- 204 No Comment:表示服务器接收的请求已成功处理,但在响应报文中不包含实体的主体部分。当从浏览器发出请求处理后,返回204,浏览器显示的页面不发生更新
- 206 Partial Content:表示客户端进行了范围请求。服务器成功执行。响应报文中包含由Content-Range指定范文的实体内容
- 301 Moved Permanently:永久重定向。表示请求的资源被分配了新的URI,应该使用资源现在所指的URI
- 302 Found:临时重定向。表示请求的资源已被分配了新的URI,希望用户本次使用新的URI访问
- 303 See Other:表示请求的资源存在着另一个URI,应该用GET方法定向获取请求的资源。
301、302、303响应状态码返回时,几乎所有的浏览器都会把POST改成GET,并删除报文内的主体,之后请求会自动再次发送
- 304 Not Modified:表示资源已找到,但未满足条件。并且在响应的主体部分不包含任何内容
- 307 Temporary Redirect:临时重定向。但是它并不会把POST变成GET
- 400 Bad Request:表示请求报文中存在语法错误
- 401 Unauthorized:表示发送的请求需要有HTTP认证(BASIC认证、DIGEST认证)的认证信息。返回401的响应必须包含一个适用于被请求资源的WWW-Authenticate首部用以质询(challenge)用户信息。初次收到401响应,会弹出认证用的对话窗口
- 403 Forbidden:表示请求资源的访问被服务器拒绝了
- 404 Not Found:表示在服务器上无法找到请求的资源
- 500 Internal Server Error:表示服务器端在执行请求时发生了错误
- 503 Service Unavailable:表示服务器暂时处于超负载或正在进行停机维护,无法处理请求。服务端在响应的时候可以写入RetryAfter首部字段来告诉客户端多久之后再来尝试
几个名词:代理
、网关
、隧道
。
- 代理:一种有转发功能的应用程序。扮演“中间人”的角色
- 网关:转发其他服务器通信数据的服务器
- 隧道:在相隔甚远的客户端和服务器之间进行中转,保持双方通信连接的应用程序
了解HTTP首部
对于HTTP报文首部,在请求的报文中主要由方法、URI、HTTP版本和HTTP首部字段(请求首部、通用首部、实体首部)等组成,在响应的报文中主要由HTTP版本、状态码(数字和原因短语)和HTTP首部字段(响应首部、通用首部、实体首部)等构成。
在客户端和服务器通过HTTP进行通信时,使用首部字段可以起到传递额外重要信息的作用。首部字段类型可以分为4种:
- 通用首部字段:请求和响应都会用到的首部
首部字段 | 代表的信息 |
---|---|
Cache-Control | 控制缓存的行为 |
Connection | 逐条首部、连接的管理 |
Date | 创建报文的日期时间 |
Pragma | 报文指令 |
Trailer | 报文末端的首部一览 |
Transfer-Encoding | 指定报文主体的传输编码方式 |
Upgrade | 升级为其他协议 |
Via | 代理服务器的相关信息 |
Warning | 错误通知 |
- 请求首部字段:补充请求的附加内容
首部字段 | 代表的信息 |
---|---|
Accept | 用户代理可处理的媒体类型 |
Accept-Charset | 优先的字符集 |
Accept-Encoding | 优先的内容编码 |
Accept-Language | 优先的语言(自然语言) |
Authorization | 报文末端的首部一览 |
From | 用户的电子邮箱地址 |
Host | 请求资源所在服务器 |
Expect | 期待服务器的特定行为 |
If-Match | 比较实体标记(ETag) |
If-Modified-Since | 比较资源的更新时间 |
If-None-Match | 比较实体标记(与If-Match相反) |
If-Range | 资源未更新时发送实体Byte的范围请求 |
If-Unmodified-Since | 比较资源的更新时间(与If-Modified-Since相反) |
Max-Forwards | 最大传输逐条数= |
Proxy-Authorization | 代理服务器要求客户端的认证信息 |
Range | 实体的字节范围请求 |
Referer | 对请求中 URI 的原始获取方 |
TE | 传输编码的优先级 |
User-Agent | HTTP 客户端程序的信息 |
- 响应首部字段:补充响应的附加内容
首部字段 | 代表的信息 |
---|---|
Accept-Ranges | 是否接受字节范围请求 |
Age | 推算资源创建经过时间 |
ETag | 资源的匹配信息 |
Location | 令客户端重定向至指定URI |
Proxy-Authenticate | 代理服务器对客户端的认证信息 |
Retry-After | 对再次发起请求的时机要求 |
Server | HTTP服务器的安装信息 |
Vary | 代理服务器缓存的管理信息 |
WWW-Authenticate | 服务器对客户端的认证信息 |
- 实体首部字段:请求和响应都会用到,补充资源内容更新时间等与实体有关的信息
首部字段 | 代表的信息 |
---|---|
Allow | 资源可支持的HTTP方法 |
Content-Encoding | 实体主体适用的编码方式 |
Content-Language | 实体主体的自然语言 |
Content-Length | 实体主体的大小(单位:字节) |
Content-Location | 替代对应资源的URI |
Content-MD5 | 实体主体的报文摘要” |
“Content-Range | 实体主体的位置范围 |
Content-Type | 实体主体的媒体类型 |
Expires | 实体主体过期的日期时间 |
Last-Modified | 资源的最后修改日期时间 |
上述具体4部分的字段类型摘录自书中,可以翻阅书籍进行更详细的了解
了解HTTPS
使用HTTP主要的不足是:
- 通信使用明文(不加密),内容可能会被窃听
- 不验证通信方的身份,因此有可能遭遇伪装
- 无法证明报文的完整性,所以有可能已遭篡改
目前比较普遍的防止被窃听的做法中,最普遍的还是加密技术。对于加密的对象可以有如下几种:
- 通信的加密:通过使用SSL(Secure Socket Layer,安全套接层)或TLS(Transport Layer Security,安全层传输协议)的组合使用,来对通信内容进行加密。SSL用来建立安全通信线路,然后使用HTTP进行通信,因此SSL组合HTTP被称为HTTPS(HTTP Secure)
- 内容的加密:即对报文主体进行加密,报文首部不加密
对于验证通信方的身份,SSL使用一种称为证书的手段,来确定对方。证书通常由值得信赖的第三方机构颁发,用来证明服务器和客户端是实际存在的
对于报文的完整性,一般使用MD5或者SHA-1等散列值校验的方法或者用来确认文件的数字签名方法。
HTTP + 加密 + 认证 + 完整性保护 = HTTPS
HTTPS不是一种新的协议,而是在HTTP通信的时候接入和SSL和TLS。使用HTTP的时候,是HTTP直接和TCP通信,再接入SSL之后,HTTP先和SSL通信,然后SLL再和TCP进行通信,因此HTTPS可以说是披着SSL外壳的HTTP。如下图
加入SSL协议之后的各层之间的关系(截取自书中)
大家可能对上文中SSL和TLS有点疑惑。其实TSL是以SSL为原型开发的协议,有时都称为SSL。当前用的版本是SSL3.0和TSL1.0。通常使用SSL的时候,处理速度会变慢,原因是:通信比较慢,因为要进行一些通信处理,交换密钥,加密解密之类,另一方面是会消耗CPU和内存等硬件资源,如下图
HTTPS要比HTTP慢(截取自书中)对于HTTPS的加密,其采用一种混合加密的机制。即采用共享秘钥和公共秘钥进行加密。客户端和服务器在交换密钥是使用公开秘钥进行加密,之后的建立通信交换报文阶段使用共享密钥进行加密。
了解一下公开密钥加密:首先公开秘钥可以公布给任何人。假如我是客户端,服务器拿到我的公开密钥之后,使用我的公开密钥对数据进行加密后,发给我,然后我用自己的私钥进行解密。反之亦然
了解一下共享秘钥加密:加密和解密都用同一个秘钥
了解了共享和公开秘钥加密之后,也就可以了解HTTPS的混合加密机制了。也可以配合下图进行理解
HTTPS混合加密机制(截取自书中)
证书的作用是用来证明公开秘钥的正确性,因为假如和某个服务器建立公开秘钥加密方式下的通信时,需要证明收到的公开秘钥就是我们要通信的那台服务器,因为存在在通信过程中,公开秘钥被替换的风险,如果被替换了,那么与之通信的,将可能是攻击者的服务器。因此一般都使用数字认证机构(CA,Certificate Authority)和其他相关机关颁发的公开秘钥证书。可参见下图进行理解
了解证书的整体作用流程(截取自书中)仔细阅读完上图之后,还需要知道的是:认证机关的公开密钥必须安全的交到客户端的手中,因此,大多的浏览器都会事先植入认证机关的公开秘钥到浏览器中
证书的另外一个作用是可以证明服务器背后运行的企业是否真实存在,持有这种特性的证书叫做EV SSL证书(Extended Validation SSL Certificate),它是基于国际标准的认证指导方针颁发的证书。
了解认证
通过认证可以确保访问服务器的人是出自本人的行为,就就是表明了使用者的身份。HTTP1.1的认证有如下几种:
- BASIC认证(基本认证,不常用)
- DIGEST(摘要认证)
-
SSL客户端认证
步骤(前提是客户端已经安装了客户端证书):- 收到需要认证资源的请求,服务器发送Certificate Request报文,要求客户端提供证书
- 客户端把证书信息以Client Certificate报文方式发送给服务器
- 服务器验证客户端证书通过后拿到客户端的公开密钥,利用https加密通道进行通信
-
FormBase认证(基于表单认证)
一般使用Cookie来管理Session
FormBase认证(截取自书中)
另外对于密码,通常是先给密码加盐,再使用散列(hash)保存明文密码。
简单了解之后,可以参考几篇HTTP方面的文章和面试题加强一下
网友评论