之前有一篇博文介绍了使用长轮询解决某些场景的实时消息推送需求,其中提到了一个spring-web中的一个类DeferredResult
,它封装了Servlet3.0提供了基于servlet的异步处理api,可以方便的实现http请求的挂起及异步的返回响应。这里再介绍一个技术SSE,也可以实现类似的需求。
什么是SSE
SSE(Server-Sent Events)是一种由服务器推送实时更新到浏览器的技术。与传统的轮询(polling)和长轮询(long polling)不同,SSE允许服务器主动向客户端发送更新,而无需客户端频繁发起请求。这种技术基于HTTP协议,采用了标准的浏览器支持的API,能够实现单向的实时数据流传输。
代码演示
新建一个springboot工程,创建以下Controller
@RestController
public class SseController {
private SseEmitter sseEmitter = new SseEmitter(60000L);
@GetMapping("/sse")
public SseEmitter sse() {
return sseEmitter;
}
@GetMapping("/setSse")
public String setSse(String message) throws IOException {
sseEmitter.send(message);
return "操作成功," + message;
}
@GetMapping("/completeSse")
public String completeSse() {
sseEmitter.complete();
sseEmitter = new SseEmitter(60000L);
return "操作成功";
}
}
这里调用/sse接口返回了一个SseEmitter
对象,该对象构造函数需要传一个超时时间,这里给的60秒,调用该接口,http请求会被挂起60秒,期间如果我们调用/setSse接口,可以拿到该对象,调用send
方法时,被挂起的接口会收到发来的消息,并且请求依旧是挂起状态,期间可以多次接收消息。
相比于DeferredResult
请求挂起后,只能接受一次消息,SseEmitter
可以在指定的超市时间内多次接收服务器推送来的消息,在某些场景下更加适合。如:
- 实时通知:如社交媒体的即时更新、实时评论等。
- 股票行情更新:实时获取股票市场数据。
- 游戏:多人游戏中实时状态的更新。
- 实时数据监控:如在线系统的日志监控。
前端只需要创建EventSource
对象添加对应的监听回调即可
// 创建 EventSource 实例来接收服务器推送的事件
const eventSource = new EventSource('/sse');
eventSource.onmessage = (event) => {
// 当接收到事件时更新当前时间
this.currentTime = event.data;
};
评论区