题目重点:用单 Admin 顺序编辑日志简化冲突,重点处理快照加增量、断线重放和执行隔离。
题意与假设
这道练习题保留了面经中值得训练的核心约束,并将需要澄清的条件单独列出。现场拿到变体时,先和面试官确认这些条件。
- 单个 session 同时只有一个有写权限的 Admin;Viewer 只读。文本规模、并发人数、Admin 移交规则未给。
- 方案用服务端单调版本和编辑日志,不以 OT/CRDT 解决不存在的并发多写;代码执行只讲隔离边界。
解题路线
- 保存 session_id、文档快照、version、Admin 身份和角色权限。客户端提交 edit(base_version, range, replacement),服务端验证写权限、串行化、持久化并分配递增 version,再广播。
- 迟加入者先订阅或获取可重放水位,再读取 version=v 的快照并应用所有 version>v 的编辑;若先读快照后直接订阅而没有补偿,竞态间隙会漏改动。
- Viewer 按 version 顺序应用增量;遇跳号则从日志补齐或重新取快照。WebSocket 推送、HTTP 快照/补偿;客户端本地乐观编辑不改变服务端最终顺序。
- Admin 变更用权限版本/租约拒绝旧 Admin 写入。多实例按 session_id 分区顺序化,广播层可横向扩展。代码执行拿固定 version 的源码交给隔离 worker,限制 CPU/内存/网络和时间,结果带 version 防旧结果覆盖新文本。
手动走一遍
Viewer 拿到快照 v40 时 Admin 同时提交 v41;Viewer 已订阅 v41 或按快照水位重放,最终到 v41。只读完快照才建立订阅而不重放,会漏掉 v41。
规模与取舍
长度 L 的快照传输 O(L),单次长度 Δ 的编辑发给 V 个 Viewer 出站约 O(VΔ)。日志随编辑数增长,周期快照使恢复重放仅覆盖最近若干编辑;题目无 QPS/用户数。
易错点与追问
容易失分的边界
- 单写题一开始就引入复杂 OT/CRDT。
- 先读快照再订阅却无水位补偿。
- 断线后只重连 WebSocket、不补跳号。
- Viewer 仅前端禁用编辑,服务端没鉴权。
- 代码执行直接运行在会话服务器进程。
继续深挖
- Admin 断线或移交时如何防双写?
- Viewer 很多时怎么扩广播?
- 日志何时压成快照?
- 旧代码执行结果怎么展示?
