websocket以及http的区别笔记

928 阅读4分钟

区别

'http'

HTTP1.1默认使用持久连接(persistent connection),在一个TCP连接上也可以传输多个Request/Response消息对,但是HTTP的基本模型还是一个Request对应一个Response

链接方式:主要有几种

  • 轮询(polling),轮询就会造成对网络和通信双方的资源的浪费,且非实时。
  • 长轮询,客户端发送一个超时时间很长的Request,服务器hold住这个连接,在有新数据到达时返回Response,相比1,占用的网络带宽少了,其他类似。稳定性有待考究
  • 长连接,其实有些人对长连接的概念是模糊不清的,我这里讲的其实是HTTP的长连接(1)
  • 如果你使用Socket来建立TCP的长连接(2)

  • 那么,这个长连接(2)跟我们这里要讨论的WebSocket是一样的,实际上TCP长连接就是WebSocket的基础,但是如果是HTTP的长连接,本质上还是Request/Response消息对,仍然会造成资源的浪费、实时性不强等问题。

    长链接

websocket的协议基础基于http 握手+传输

而真正在WS的握手过程中起到作用的是下面几个header域。
1 Upgrade:upgrade是HTTP1.1中用于定义转换协议的header域。它表示,如果服务器支持的话,客户端希望使用现有的「网络层」已经建立好的这个「连接(此处是TCP连接)」,切换到另外一个「应用层」(此处是WebSocket)协议。

2 Connection:HTTP1.1中规定Upgrade只能应用在「直接连接」中,所以带有Upgrade头的HTTP1.1消息必须含有Connection头,因为Connection头的意义就是,任何接收到此消息的人(往往是代理服务器)都要在转发此消息之前处理掉Connection中指定的域(不转发Upgrade域)。
如果客户端和服务器之间是通过代理连接的,那么在发送这个握手消息之前首先要发送CONNECT消息来建立直接连接。

3 Sec-WebSocket-*:第7行标识了客户端支持的子协议的列表(关于子协议会在下面介绍),第8行标识了客户端支持的WS协议的版本列表,第5行用来发送给服务器使用(服务器会使用此字段组装成另一个key值放在握手返回信息里发送客户端)。

4 Origin:作安全使用,防止跨站攻击,浏览器一般会使用这个来标识原始域。

  • WebSocket协议Uri
1 如果上一步中的TCP连接建立失败,则此WebSocket连接失败。
2 如果协议是wss,则在上一步建立的TCP连接之上,使用TSL发送握手信息。如果失败,则此WebSocket连接失败;如果成功,则以后的所有数据都要通过此TSL通道进行发送。
  • WebSocket使用注意点

服务端 如果请求是HTTPS,则首先要使用TLS进行握手,如果失败,则关闭连接,如果成功,则之后的数据都通过此通道进行发送

之后服务端可以进行一些客户端验证步骤

如果一切都成功,则返回成功的Response握手消息。

  • 服务端发送的成功的Response握手

Upgrade头域,内容为websocket

Connection头域,内容为Upgrade

Sec-WebSocket-Accept头域,其内容的生成步骤:

首先将Sec-WebSocket-Key的内容加上字符串258EAFA5-E914-47DA-95CA-C5AB0DC85B11(一个UUID)。

将#1中生成的字符串进行SHA1编码。

将#2中生成的字符串进行Base64编码。

  • Sec-WebSocket-Protocol头域(可选)
  • Sec-WebSocket-Extensions头域(可选)
与HTTP比较
同样作为应用层的协议,WebSocket在现代的软件开发中被越来越多的实践,和HTTP有很多相似的地方,这里将它们简单的做一个纯个人、非权威的比较:

相同点:
都是基于TCP的应用层协议。
都使用Request/Response模型进行连接的建立。
在连接的建立过程中对错误的处理方式相同,在这个阶段WS可能返回和HTTP相同的返回码。
都可以在网络中传输数据。

不同点:
WS使用HTTP来建立连接,但是定义了一系列新的header域,这些域在HTTP中并不会使用。
WS的连接不能通过中间人来转发,它必须是一个直接连接。
WS连接建立之后,通信双方都可以在任何时刻向另一方发送数据。
WS连接建立之后,数据的传输使用帧来传递,不再需要Request消息。
WS的数据帧有序。
```