双向通讯方式

常见的双向通信方式包括 HTTP 短轮询(polling)、HTTP 长轮询(long-polling)、XHR Streaming、Server-Sent Events、Websocket 等。

其中,最简单粗暴的莫过于 HTTP 短轮询,客户端每隔特定的时间(比如 1s)便向服务端发起请求,获取最新的资源信息。该方式会造成较多的资源浪费,尤其当服务端内容更新频率低于轮询间隔时,就会造成服务端资源、客户端资源的浪费。除此之外,过于频繁的请求也会给服务端造成额外的压力,当服务端负载较高的时候,甚至可能导致雪崩等情况发生。

HTTP 长轮询解决了短轮询的一些问题,长轮询实现特点主要为当客户端向服务端发起请求后,服务端保持住连接,当数据更新响应之后才断开连接。然后客户端会重新建立连接,并继续等待新数据。此技术的主要问题在于,在重新连接过程中,页面上的数据可能会过时且不准确。

相比 HTTP 长轮询,XHR Streaming 可以维护客户端和服务端之间的连接。但使用 XHR Streaming 过程中,XMLHttpRequest 对象的数量将不断增长,因此在使用过程中需要定期关闭连接,来清除缓冲区。

SSE(Server-Sent Events)方案思想便是 XHR Streaming,主要基于浏览器中 EventSourceAPI 的封装和协议。它会对 HTTP 服务开启一个持久化的连接,以 text/event-stream 格式发送事件,会一直保持开启直到被要求关闭。

最后我们来介绍 WebSocket,它实现了浏览器与服务端全双工通信。前面我们提到,HTTP 短轮询、长轮询都会带来额外的资源浪费,因此 Websocket 在实现实时通信的同时,能更好地节省服务端资源和带宽。

由于不再需要通过 HTTP 协议通信,省去请求头等内容设置,Websocket 数据格式会更加轻量,通信更加高效,性能开销也相应地降低。除此之外,不同于 HTTP 协议,Websocket 协议没有同源限制,因此客户端可以与任意服务端通信。