GoForum🌐 V2EX

[独立开发] 既然不做 99.99% SLA,我决定用“空手套白狼”解决分布式竞态问题

kai92zeng · 2026-01-24 21:17 · 0 次点赞 · 2 条回复

前言:完美的架构,失效了? 我是个写 Rust 的独立开发者。在我的交易模拟系统里,我引以为傲地设计了一套纯内存的领域事件驱动架构。

没有 Kafka ,没有 RabbitMQ ,就靠 Rust 强大的内存通道,实现了微秒级的模块解耦。交易服务只管平仓,根本不需要关心是谁在发通知、是谁在算奖励。

直到有一天,我发现了一个幽灵般的 Bug 。

第一章:消失的奖励( The Race Condition ) 场景很简单:用户注册成功 -> 后端发放“新手大礼包” -> 推送弹窗通知。

逻辑看起来天衣无缝:后端提交注册事务,紧接着发送一个“注册成功”的内部事件。

然而测试发现,用户注册进去了,奖励也发了,但前端死活收不到弹窗。

排查日志后,我发现这是一个经典的分布式竞态条件( Race Condition )。虽然我是单体应用,但前后端在时间维度上是割裂的:

后端(光速):事务提交、触发事件、计算奖励、尝试 Websocket 推送。此时发现用户尚未建立连接(因为是刚注册完),于是只能两手一摊,丢弃消息。

前端(龟速):收到注册成功 200 OK ,保存 Token ,初始化 SDK ,请求个人信息,最后才建立 Websocket 连接。

这就好比:后端这边的发令枪响了,奖杯也扔出去了,前端的运动员还在系鞋带。等他抬起头,奖杯早就摔碎在底上了。

第二章:教科书式的“正确”方案( The Inbox Pattern ) 遇到这种“发太快、连太慢”的问题,资深架构师(其实就是我自己)的第一反应是:上持久化,用信箱模式( Inbox Pattern )!

方案极其正统:

建表:搞个“用户通知表”。

落库:不管用户在不在,消息先插进数据库,标记为“未读”。

推拉结合:后端试着推一下;前端连上 WS 后,立马调一个 HTTP 接口拉取未读消息。

这个方案完美吗?完美。可靠性高吗?极高。 但我看着手里的键盘,犹豫了。

作为一个独立开发者,为了这就加一张表?写一套 CRUD ?前端还得改逻辑去轮询?如果未来我有 10 种消息都要这么搞,数据库会不会爆炸?我只有一双手,我要的是功能上线,不是在代码里建一座大教堂。

“复杂性是独立开发者的墓志铭。” 我把这个方案否了。

第三章:来自内存的暴力美学( The Spin-Wait ) 我开始反思:通过数据库中转,本质上是用空间(磁盘)换时间(等待)。 那我能不能直接用时间换时间?

Rust 的协程( Task )极其廉价,开几万个跟玩一样。我为什么不直接在内存里“等”前端上线呢?

于是,诞生了这个“异步自旋重试”方案。

我并没有修改复杂的架构,而是写了一个简单的“蹲守”逻辑:

当需要发送奖励而用户不在线时,后端并不会直接放弃,而是派出一个轻量级的后台协程(相当于一个临时工)。

这个协程的任务非常简单粗暴:它拿着信站在门口,每隔 0.5 秒看一眼“用户连上 Websocket 了没?”

如果连上了,立马把信塞进去,任务结束。

如果没连上,就睡一会儿再看。

如果等了 60 秒(超时阈值)还没人影,那就算了,毁灭吧。

第四章:取舍与哲学 这个方案在“架构师”眼里可能是离经叛道的:

不可靠:万一这 60 秒内服务器重启,内存里的消息就丢了。

不优雅:居然用轮询( Polling )这种原始手段?

但对于我的场景,它是最合适的:

零基础设施:不需要 Redis ,不需要新表,不需要改前端 Pull 逻辑。

极致简单:就在通知服务里加个小函数,其他地方完全无感。

用户体验:前端注册完,卡顿了 3 秒才连上,第 3.5 秒后端那个“蹲守协程”刚好醒来,把奖励推过去。用户看来就是:注册 -> 自动登录 -> 砰!奖励弹窗。丝般顺滑。

关于丢消息:如果服务器真的在那几十秒重启了,用户仅仅是少看了一个“获得奖励”的弹窗,但他账户里的钱( DB 事务保证)是一分不少的。这个 SLA ,我可以接受。

结语 我们在做架构设计时,往往容易陷入“大厂思维”的陷阱,追求理论上的完美和绝对的可靠。

但在独立开发的世界里,代码量越少,Bug 越少;依赖越少,睡得越香。

用 Rust 的高性能去弥补架构的“土”,用内存的易失性去换取开发的“快”。这就是我作为一个 CRUD Boy 的生存之道。

2 条回复
Sunyin · 2026-01-24 21:32
#1

👍没有完美的架构,只有合适的架构。 技术,终究是为了业务服务的。

kai92zeng · 2026-01-24 22:07
#2

@Sunyin 古人有云:每日三省

添加回复
你还需要 登录 后发表回复

登录后可发帖和回复

登录 注册
主题信息
作者: kai92zeng
发布: 2026-01-24
点赞: 0
回复: 0