SSE 本身不提供原生分组或权限过滤,需服务端推送带元数据(如 group、role)的消息,客户端解析后按业务规则处理;服务端应预筛消息,客户端用 JSON.parse 提取 data 并分类路由,支持 Map 动态管理处理器,结合角色做前端权限过滤但须后端校验。

在 JavaScript 的 SSE(Server-Sent Events)中,本身不提供原生的“分组”或“权限过滤”能力——这些逻辑必须由前端主动处理。核心思路是:服务端按需推送带元数据(如 group、role、scope)的消息,客户端用 JavaScript 解析并根据业务规则决定是否接收、丢弃或路由到不同模块。
服务端发送带上下文的消息
SSE 消息本质是文本流,格式灵活。推荐在每条事件中嵌入结构化字段,例如:
event: message<br>data: {"id":"101","group":"team-a","role":"editor","content":"文档已更新"}
关键点:
- 使用 data 字段传递 JSON 字符串(注意换行符需转义)
- 避免在 event 字段做权限控制(它仅用于客户端 eventListener 分类)
- 服务端应基于用户登录态预筛消息,减少无效推送(减轻带宽和客户端负担)
客户端按 group 进行分组接收
监听时统一捕获所有消息,再用 JS 提取 data 并分类:
立即学习“Java免费学习笔记(深入)”;
const evtSource = new EventSource("/api/notifications");<br>evtSource.onmessage = (e) => {<br> try {<br> const msg = JSON.parse(e.data);<br> if (msg.group === "team-a") {<br> handleTeamAMessages(msg);<br> } else if (msg.group === "project-x") {<br> handleProjectXMessages(msg);<br> }<br> } catch (err) {<br> console.warn("Invalid SSE data", e.data);<br> }<br>};
更进一步可封装为 Map 存储分组处理器:
- const handlers = new Map(); handlers.set("team-a", fn)
- 收到消息后 handlers.get(msg.group)?.(msg) 动态调用
- 支持运行时增删分组监听器(如切换团队时重置 handler)
结合用户角色做前端权限过滤
权限不应只靠前端过滤(必须后端校验),但前端可增强体验:
- 从登录态或 token 中提取当前用户 role(如 "admin", "member", "viewer")
- 消息中携带 requiredRole 字段:data: {"content":"删除操作","requiredRole":"admin"}
- 客户端比对:if (currentUserRole === msg.requiredRole || isHigherPrivilege(msg.requiredRole))
- 不满足权限时可静默丢弃,或降级显示(如灰显+tooltip提示“无权限”)
避免常见陷阱
SSE 是单向流,无法像 WebSocket 那样动态订阅/退订。所以:
- 不要依赖 event 类型区分权限(如 event: admin-only)——易被绕过且扩展性差
- 避免在 onmessage 中频繁 JSON.parse 大量消息——可加节流或批量解析
- 注意 reconnect 行为:断连重连后,服务端应从 last-event-id 续推,避免重复或丢失
- 敏感操作类消息(如删除确认)务必走独立 API 校验,不可仅靠 SSE 权限字段触发


















