HTTP
应用层的HTTP做了什么事?
一般会用到以下的关键信息:
请求的地址、请求方式(GET、POST等),Header信息有什么(Accept类型,User-Agent信息等), 请求的参数如何封装,状态码表示什么含义,cookie如何处理,DNS怎么请求等等。
以上内容均不在本文的讨论环节中,请自行了解。
不足之处
HTTP的不足之处主要在于安全性,有以下几点:
- 通信使用明文,内容会被窃听。
- 没有验证对方的身份,因此会遭遇伪装。
- 无法了解response的完整性,所以有可能已经被篡改了。
Charles
Charles是一个非常常见的抓包工具,通过进行代理,使计算机交互的网络请求通过它进行中转,记录和显示所有发送和接收的数据。 开发经常用它可以做什么事?
- 截获请求,查看其中详细消息(被窃听)
- 模拟请求发送,比如repeat。(伪装请求)
- 修改发送的数据或者接受的数据。(篡改内容)
补救措施
如果只用http,有什么方式可以对第三方有一定的防范?
-
直接对交互内容进行加密。 对请求的内容或者返回的内容进行加密,需要服务端与客户端同时具备加密与解密功能,在每次发送消息,接受消息的时候都进行加密解密,这样就算被截取,也无法被识别,但是报文首部还是不能被加密。
-
HTTP的基本认证机制 对于某些涉及到敏感信息的请求,会设定一个安全域,一旦进行返回便会返回401 Unanthorized,并且要求用户输入账号与密码,在客户端进行base64加密后发送给服务端。在被窃听之后被加密之后的消息依然会被截取,如果被窃听方保存,仍然可以再一次发送给服务端,获取信任。
-
MD5校验文件
HTTPS
HTTPS 就是在安全的传输层上发送的 HTTP。HTTPS 在将 HTTP 报文发送给 TCP 之前,先将其发送给了一个安全层,对其进行加密。
HTTP 安全层是通过 SSL 及其现代替代协议 TLS 来实现的。我们遵循常见的用法,用术语 SSL 来表示 SSL 或者 TLS。

发送已加密的 HTTP 报文之前,客户端和服务器要进行一次 SSL 握手,在这个握手过程中,它们要完成以下工作:
- 交换协议版本号;
- 选择一个两端都了解的密码;
- 对两端的身份进行认证;
- 生成临时的会话密钥,以便加密信道。
在了解这个握手过程之前,需要了解对称加密与非对称加密的概念。
对称加密
服务端与客户端用相同的密钥对消息加密,这样就算攻击者劫持到了中间的消息,还是破解不了。
但是会有两个问题:
如果要让对方获得一样的密钥,总不能通过http的方式告诉对方,需要通过其他的路径。 每一个客户端使用的密钥必须得不一样,如何管理这么多的密钥。
非对称加密
客户端保存私钥,服务端接受来自客户端的公钥。
虽然公钥是可以在网上公开的,但是黑客截取到了用公钥加密的数据,没有私钥还是不能打开。
可以解决一大部分问题了,但是还是有缺点:
但是黑客也可以模拟客户端发送数据,因为它也有公钥。
如果公钥被偷偷替换了,也无法证明是否是真的公钥。
非对称加密的算法比对称加密效率要低不少。
证书加密
证书就是为了解决这个问题诞生的。
证书中包含很多信息,主要有:
- Web 站点的名称和主机名;
- Web 站点的公开密钥;
- 签名颁发机构的名称;
- 来自签名颁发机构的签名。

HTTPS通信请求详细步骤:

步骤1:客户端通过发送ClientHello报文开始SSL通信。报文中包含客户端支持的SSL的指定版本、加密组件(CipherSuite)列表(所使用的加密算法及密钥长度等)。
步骤2:服务器可进行SSL通信时,会以ServerHello报文作为应答。和客户端一样,在报文中包含SSL版本以及加密组件。服务器的加密组件内容是从接收到的客户端加密组件内筛选出来的。
步骤3:之后服务器发送Certificate报文。报文中包含公开密钥证书。
步骤4:最后服务器发送ServerHelloDone报文通知客户端,最初阶段的SSL握手协商部分结束。
步骤5:SSL第一次握手结束之后,客户端以ClientKeyExchange报文作为回应。报文中包含通信加密中使用的一种被称为Premastersecret的随机密码串。该报文已用步骤3中的公开密钥进行加密。
步骤6:接着客户端继续发送ChangeCipherSpec报文。该报文会提示服务器,在此报文之后的通信会采用Premastersecret密钥加密。
步骤7:客户端发送Finished报文。该报文包含连接至今全部报文的整体校验值。这次握手协商是否能够成功,要以服务器是否能够正确解密该报文作为判定标准。
步骤8:服务器同样发送ChangeCipherSpec报文。
步骤9:服务器同样发送Finished报文。
步骤10:服务器和客户端的Finished报文交换完毕之后,SSL连接就算建立完成。当然,通信会受到SSL的保护。从此处开始进行应用层协议的通信,即发送HTTP请求。
步骤11:应用层协议通信,即发送HTTP响应。
步骤12:最后由客户端断开连接。断开连接时,发送close_notify报文。上图做了一些省略,这步之后再发送TCPFIN报文来关闭与TCP的通信。
缺点
既然HTTPS比HTTP好,为什么不一直用HTTPS?
- 为了处理SSL层级的通信,通信量会变大。
- 在处理SSL加密解密同时,会更多的消耗服务器上的资源。
- 使用的证书需要向认证机构购买,会有一笔不小的开销。
Charles
回到Charles这个话题,为什么Charles能抓HTTP的请求?
因为Charles在服务端与客户端做了一层代理。
为什么HTTPS的请求也能截取?
还记得在截取HTTPS请求的时候,需要做什么么?
- 安装并信任Charles证书。
- 对SSL进行代理。
具体步骤:
-
客户端向服务器发起HTTPS请求
-
Charles拦截客户端的请求,伪装成客户端向服务器进行请求
-
服务器向“客户端”(实际上是Charles)返回服务器的CA证书
-
Charles拦截服务器的响应,获取服务器证书公钥,然后自己制作一张证书,将服务器证书替换后发送给客户端。(这一步,Charles拿到了服务器证书的公钥)
-
客户端接收到“服务器”(实际上是Charles)的证书后,生成一个对称密钥,用Charles的公钥加密,发送给“服务器”(Charles)
-
Charles拦截客户端的响应,用自己的私钥解密对称密钥,然后用服务器证书公钥加密,发送给服务器。(这一步,Charles拿到了对称密钥)
-
服务器用自己的私钥解密对称密钥,向“客户端”(Charles)发送响应
-
Charles拦截服务器的响应,替换成自己的证书后发送给客户端
至此,连接建立,Charles拿到了 服务器证书的公钥 和 客户端与服务器协商的对称密钥,之后就可以解密或者修改加密的报文了。
这里最关键的一步就是需要客户端信任Charles证书,这也是为什么不要安装来历不明的盗版系统的原因之一。
参考
- 趣谈网络协议
- HTTP权威指南
- 图解HTTP