外观主题
阅读语言

微服务数据边界 —— 一库一服务,跨服务只传 ID

软件 本站软件 4小时前
https://yxp.hk/p/heKs86

📦 开源仓库:learn_microservice_by_id · 纯 Python 标准库 · 学习演示项目

微服务最容易犯的错,是服务拆了、数据库还揉在一起。这个仓库用一个云盘案例讲透微服务的数据铁律:每个服务独占一个库,库之间不共享表、不建外键,服务之间只用唯一的业务 ID(user_id / product_id / order_id)串联。

为什么云盘要这么拆

云盘不是一个系统,是一堆节奏完全不同的能力:账号登录(强一致、低频)、文件元数据(读并发极高)、块存储(海量小 IO)、搜索(倒排索引)、预览(CPU 密集转码)、分享(可吊销链接)、配额计费(对账)。并发模型、数据量、技术栈、发布节奏全不一样——挤进一个库,列个文件列表能拖垮登录,改个分享逻辑能回归一切。

一库一服务买到什么:独立伸缩、独立选型、故障隔离、干净的数据边界(不再有 join users 里的 files)。

为什么用 ID 而不是共享表/外键:共享库 = 发布耦合;外键跨服务不存在。ID 是最便宜的契约——订单存 user_id,要用户信息就 HTTP 调用户服务,或订阅事件留只读副本。加功能永远不改老库的 schema。

「胶水层」的价值

不建一个大系统,而是建一堆互相不认识的小组件 + 一个编排层:

  • 组件保持极简:文件服务只按 file_id 出字节,不知道水印、杀毒、AI 摘要的存在
  • 业务变化集中在胶水:「下载前必须杀毒」改的是流程,不是零件
  • 可替换可插拔:换对象存储、换转码引擎,ID 契约不变就行
  • 容错收口一处:胶水层统一重试/降级/缓存,组件保持简单

演示:四个独立进程、四个独立 JSON 库、ID 串联

服务 端口 拥有 只引用(ID)
user 7001 users(余额) —
product 7002 products(库存) —
order 7003 orders(数量/状态) user_id、product_id
payment 7004 payments(金额/状态) order_id、user_id
  1. 正常下单:建单 → 扣余额 → 扣库存 → 记支付 → PAID;详情按 ID 实时拼装
  2. 余额不足:在余额步骤失败,库存分毫未动
  3. 库存不足:余额已扣,网关做退款补偿
  4. 按 ID 跨库拼装:订单裸行只有 ID,详情现场跨服务 join

活下来的三条铁律:处处幂等、trace-id 贯穿全链路、痛了再拆。

运行

python run_all.py

纯 Python 标准库,零第三方依赖,一键跑完所有演示场景后自动退出。
仓库:github.com/yxpil/learn_microservice_by_id,欢迎 Star 与提 Issue。