Server-Sent Events (SSE) 是一种用于实现服务器向客户端推送数据的技术。与 Ajax 和 WebSocket 不同,SSE 使用 HTTP 协议,因此能够在不支持 WebSocket 的环境下使用。相比较于 Ajax 轮询,SSE 拥有更低的延迟和更高的效率。但是,SSE 却存在一个问题:一旦连接断开,就需要通过重连机制重新建立连接。
SSE 原理
SSE 的原理是使用独立的 HTTP/TCP 连接,使得服务端可以通过这个连接向客户端发送数据。客户端使用 EventSource API 与服务端建立连接,并通过注册事件句柄接收服务端发送的信息。
服务端发送的数据使用文本格式,以 "data:" 开头,以 "\n\n" 结尾,例如:
data: hello world
客户端通过监听 "message" 事件处理函数接收数据:
const eventSource = new EventSource('/stream'); eventSource.addEventListener('message', function(event) { console.log('Received message:', event.data); });
此外,SSE 还支持事件类型(event),用于区分不同类型的消息,以及 ID 字段,用于识别消息的唯一性。
断开连接后的重连机制
由于 SSE 使用的是 HTTP/TCP 连接,因此在网络不稳定或者发生其他异常情况时,连接可能会断开。为了保证数据的稳定传输,SSE 需要通过重连机制来重新建立连接。
首先,客户端需要监听 "error" 事件,以便检测连接是否断开:
const eventSource = new EventSource('/stream'); eventSource.addEventListener('error', function(event) { console.log('Connection error:', event); });
然后,我们需要实现一个重连函数,用于重新建立连接:
-- -------------------- ---- ------- -------- ---------------------- - ------------------------------- --------------------- - ----------- - --- ----------------------- --------------------------------------- --------------- - --------------------- ---------- ------------ --- ------------------------------------- --------------- - ----------------------- --- -- ------ -- - ------ -展开代码
当连接断开时,重连函数将会被调用,并在 1 秒后尝试重新建立连接。在重新连接过程中,客户端需要重新注册 "message" 事件和 "error" 事件,以便处理新的数据和连接异常。
示例代码
下面是一个完整的示例代码,对 SSE 断开连接后的重连机制进行了实现:
服务端代码:
-- -------------------- ---- ------- -- -------- ----- ---- - ---------------- ------------------------------- ---- - ------------------ - --------------- -------------------- ---------------- ----------- ------------- ------------ --- ---------------------- - ---------------- - - --- --------------------------- - -------- -- ------ --------------- ---------- - ------------------- --------- -- ---- ---------- ---展开代码
客户端代码:
-- -------------------- ---- ------- -- ---------- --------- ----- ------ ------ ----- ---------------- ------- ------ -------- ----- ----------- - --- ----------------------- --------------------------------------- --------------- - --------------------- ---------- ------------ --- ------------------------------------- --------------- - ----------------------- --- -------- ---------------------- - ------------------------------- --------------------- - ----------- - --- ----------------------- --------------------------------------- --------------- - --------------------- ---------- ------------ --- ------------------------------------- --------------- - ----------------------- --- -- ------ -- - ------ - --------- ------- -------展开代码
运行上面的代码,打开浏览器访问 "http://localhost:8080",可以在控制台中看到每秒钟输出一个时间戳。在控制台中,可以模拟网络中断的情况,观察断开连接后的重连过程。
来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/67c283b7314edc2684bd7a18