主 题
博客系统自文档 · 第 11/16 篇
目录 · 上一篇:RPG 技术实现 · 下一篇:安全与限流
写在前面
系统里有两条「事件」通路,不要混为一谈:
- Redis Stream — 可靠异步、跨模块解耦
- WebSocket — 即时 UI、在线用户
功能与体验
读者发评论后:
- 评论立刻出现在详情页(HTTP 同步)
- 作者铃铛亮起(WebSocket
siteNotification) - 作者/读者 RPG 经验稍后增加(Stream 消费)
用户感知是「同时进行」,实现上分两条链路。
设计与实现
flowchart TB
subgraph sync [同步 HTTP]
API[Feature Service]
API --> MySQL[(MySQL)]
end
subgraph async [异步 Stream]
Pub[BlogEventPublisher]
Stream[(blog:events)]
Consumer[rpg-event.consumer]
Pub --> Stream --> Consumer --> MySQL
end
subgraph realtime [实时 WS]
GW[RealtimeGateway]
GW --> Browser[浏览器]
end
API --> Pub
API --> GW
BlogEventPublisher
位于 core/events/,发布如:
| 事件 | 典型触发 |
|---|---|
ARTICLE_PUBLISHED |
发文 status=publish |
COMMENT_CREATED |
新评论 |
USER_REGISTERED |
注册完成 |
Payload 含 uid、articleId 等,consumer 幂等处理。
何时用 Stream vs WS
| 场景 | 选型 | 原因 |
|---|---|---|
| 加经验、成就 | Stream | 可堆积、可重放、与 HTTP 解耦 |
| 升级弹窗、通知角标 | WS | 必须在线即时 |
| 定时发文 | Cron + DB | 非事件总线 |
扩展新事件
BlogEvents常量 + publisher 调用点rpg-event.consumer或新 consumer 订阅- 若需 UI 反馈,再
RealtimeGateway.pushToUser
踩坑与取舍
- SQL 直写 article 不发 Stream:自文档 SQL 导入无 RPG 经验,属预期。
- Consumer 失败:需监控 Stream pending;生产应日志 + 告警。
- 两套都要 Redis:Stream 与 Socket.IO Adapter 共用 ioredis 实例,键空间不同。
系列导航
- 导读 · 第 0 篇
- 下一篇:12 安全与限流
延伸阅读
core/events/rpg/listeners/rpg-event.consumer.ts

全部评论(0)