Contents

服务端消息推送方案总结

HTTP 协议存在一个问题是只能单向通信,即通信只能由客户端向服务器发出请求,服务器返回查询结果。HTTP 协议做不到服务器主动向客户端推送信息。但是有一些场景需要服务器通知客户端。可用的方案如下:

  • 短轮询
  • 长轮询
  • iframe
  • websocket
  • sse

短轮询

客户端每隔一段时间就向服务器发出HTTP请求,服务器端在收到请求后,不论是否有数据更新,都直接进行响应。

优点:实现简单。

缺点:

  • 轮询的间隔过长,会导致不能及时接收到更新数据。轮询的间隔过短,会导致查询请求过多,增加服务器端的负担。
  • 需要不断进行请求,浪费服务器端和客户端资源,加大服务器端压力。

长轮询

首先由客户端向服务器发起请求,当服务器收到客户端发来的请求后,服务器端不会直接进行响应,而是先将 这个请求挂起,然后判断服务器端数据是否有更新。如果有更新则进行相应,如果一直没有数据,则到一定时间限制才返回。客户端处理返回的信息后,再次发出请求,重新建立连接。

优点:

  • 相比短轮询,减少了很多不必要的 http 请求次数,节约带宽。
  • 有较好的时效性。

缺点:

  • 保持连接也会导致资源浪费。

WebSocket

WebSocket是一种在TCP连接上进行全双工通信的协议,建立客户端和服务器之间的通信渠道。浏览器和服务器仅需一次握手,两者之间就直接可以创建持久性的连接,并进行双向数据传输。

优点:

  • 全双工协议,支持双向通信,实时性更强。也就是通信双方是平等的,可以相互发送消息。
  • 支持跨域。
  • 减少通信量:只要建立起WebSocket连接,就希望一直保持连接状态。和HTTP相比,不但每次连接时的总开销减少,而且由于WebSocket的首部信息很小,通信量也相应减少了。在海量并发和客户端与服务器交互负载流量大的情况下,极大的节省了网络带宽资源的消耗,有明显的性能优势,且客户端发送和接受消息是在同一个持久连接上发起,实时性优势明显

缺点:

  • WebSocket是一个新的协议,需要服务器端支持,服务器端配置比较复杂。

SSE

服务器发送事件(Server-sent events),简称SSE,可以实现服务器端到客户端(浏览器)的单项消息推送。

SSE它是基于HTTP协议的,一般意义上的HTTP协议是无法做到服务端主动向客户端推送消息的,但SSE是个例外,它变换了一种思路。SSE在服务器和客户端之间打开一个单向通道,服务端响应的不再是一次性的数据包而是text/event-stream类型的数据流信息,在有数据变更时从服务器流式传输到客户端。

优点:

  • 部署在 HTTP协议之上的,现有的服务器软件都支持。

缺点:

  • 网站需支持Http2.0。
  • 不支持跨域。

与WebSocket区别:

  • SSE 是基于HTTP协议的,不需要额外的协议即可工作;WebSocket需要服务器配置支持。

  • SSE 单向通信,只能由服务端向客户端单向通信;webSocket双向通信,即通信的双方可以同时发送和接受信息。

  • SSE 实现简单开发成本低,无需引入其他组件;WebSocket传输数据需做二次解析,开发门槛高一些。

  • SSE 默认支持断线重连;WebSocket则需要自己实现。

  • SSE 只能传送文本消息,二进制数据需要经过编码后传送;WebSocket默认支持传送二进制数据。

方式 类型 优点 缺点 适用场景
短轮询 client→server 实现简单。 1. 浪费资源。2. 存在延迟。 适于小型应用
长轮询 client→server 实现简单。 保持连接消耗资源。 WebQQ、Hi网页版、Facebook IM
WebSocket server⇌client 1. 支持双向通信。2. 可发送二进制文件。3. 性能好 开发成本高 网络游戏、银行交互和支付等需要双向通信的场景。
SSE server→client 实现简单。 需要网站支持。 消息通知等只需要单向通信的场景

参考资料

各类“服务器推”技术原理与实例(Polling/COMET/SSE/WebSocket)