本篇要搞懂的 4 件事:事件风暴是个什么活动、开工前要准备什么(人/物/场地/关注点)、用「用户中台」当例子走一遍从想法到领域模型的四个阶段、领域模型为什么不能直接拍板成微服务。
⚠️ 这是一篇操作手册式的章节——前面几讲在讲"DDD 里有哪些概念"(实体、聚合、限界上下文),这一讲在讲"拿什么工具、按什么步骤,把这些概念真正画出来"。它把抽象理论第一次落到了具体动作上。
承接前文:前面我们认识了 DDD 的一堆零件——实体、值对象、聚合、聚合根、限界上下文、领域事件。但有个一直悬着的问题:这些东西到底是怎么从一堆杂乱的业务需求里被"找"出来的? 第 12 讲给的答案就是 事件风暴(Event Storming)。它是一个把领域专家和开发团队拉到一面墙前、用便利贴一步步把领域模型贴出来的工作坊。这一讲全程用「用户中台」当案例,带你走完 产品愿景 → 业务场景分析 → 领域建模 → 微服务拆分 这四步。
前面几讲:DDD 有哪些零件(实体/聚合/限界上下文……)
第 12 讲:用「事件风暴」这个工具,把零件从业务里找出来、拼成领域模型
↓ 四个阶段
产品愿景 → 业务场景分析 → 领域建模 → 微服务拆分与设计
🪞 辅助理解(事件风暴是什么):你可以把它想成一群人用便利贴破案。墙是案板,不同颜色的便利贴是不同的线索(谁干的、干了什么、结果是什么),大家一起把线索贴上墙、连成因果链,最后归纳出"这个领域里到底有哪些角色、哪些东西、该怎么分块"。它不是一个人闷头画 UML,而是一群人边吵边贴。
事件风暴是怎么运转的?
先看它的"游戏规则":领域专家和项目团队一起开个工作坊,用头脑风暴把领域里所有的"领域事件"都罗列出来(比如"用户已创建"“岗位已分配”),整合成一个事件集合;然后给每个事件倒推:是什么"命令"触发了它?这个命令又是谁(哪个角色/实体)发起的?命令可以是用户点的、第三方系统调的、定时器触发的。最后把这些事件分类,整理出实体、聚合、聚合根、限界上下文。
💡 注意这个倒推的方向:事件风暴是从"结果"往回找"原因"——先有"用户已创建"这个事实,再问"谁、用什么命令、把它做出来的"。这和我们平时"先想功能再写代码"的顺序正好相反,也是它最反直觉、最值得练的地方。
开工前要准备什么?
准备 1:人——领域专家是核心
事件风暴是个工作坊(workshop),靠"可视化 + 高互动"把模型一步步逼出来。其中领域专家不可或缺。
🪞 辅助理解(领域专家是谁):就是那个"业务活字典"——不光知道业务怎么做,还知道为什么要这么做。很多公司没有挂这个头衔的人,没关系,从下面这些人里挑就行。
| 角色 | 能不能当领域专家 |
|---|---|
| 业务人员 / 需求分析师 / 产品经理 | ✅ 对业务理解深的优先 |
| 在这个领域干了多年的开发 | ✅ 懂业务"为什么"的优先 |
| 其他参与者:架构师、项目经理、开发、测试、DDD 专家 | 一起参与,但不算领域专家 |
💡 为什么要全员尽早参与?因为领域建模本质是**统一团队语言(通用语言 Ubiquitous Language)**的过程。大家在墙前一起把"用户"“账户”"认证票据"这些词的含义吵清楚、对齐了,后面写代码、拆微服务时才不会各说各话、对不上。
准备 2:物——便利贴 + 笔
参与者把想法写在即时贴(便利贴)上,贴到墙上合适位置,作者戏称这叫"刷墙"。所以便利贴和水笔是必备,再备点胶带/磁扣方便随时挪位置。关键是用不同颜色区分不同的领域行为:
看图抓什么:记住这四个颜色,后面所有图都靠它读懂——蓝=命令(谁发起的动作)、绿=实体、橙=领域事件(动作产生的结果/事实)、黄=补充信息(注意事项、外部依赖说明)。作者强调颜色不固定,团队内统一才是重点。
准备 3:场地——一堵墙 + 一片空地
不需要会议室、投影、椅子!只要一堵够长的墙(贴纸用)和一片够大的空地(让人四处走动)。作者甚至说,撤掉桌椅反而效率更高。事件风暴的发明者建议准备八米长的墙,免得设计被空间限制——当然这不是硬性要求,别让思维受限就行。
🪞 辅助理解(为什么撤桌椅):坐着开会人会犯困、会闷头刷手机;站着围墙走来走去,人就被"激活"了,更愿意上手贴、上手挪。这是个体力活 + 集体活,不是听讲座。
准备 4:关注点——盯着业务里的"动词和名词"
建模时重点听这类语言:某个业务动作(事件)会不会触发下一个动作?这个动作的输入输出是什么?是谁(实体)发出了什么动作(命令)、触发了这个事件?从这些暗藏的词里,就能扒出事件、命令、实体这些领域对象。
💡 一句话口诀:名词大概率是实体,动词大概率是命令,"……已完成"这种过去式大概率是领域事件。 听业务专家讲话时,脑子里就按这三类去归。
实战四步:用「用户中台」走一遍
整个领域建模分四个阶段。下面全程拿"用户中台"举例(一个集中管理用户、权限、认证的中台产品)。
第一步:产品愿景——先对齐"我们到底要做个啥"
产品愿景是给产品做顶层价值设计,让目标用户、核心价值、差异化竞争点达成一致,避免做着做着方向跑偏。
做法:参与者对左侧每一类问题(为了…、他们的…、这个…、是一个…、它可以…、而不像…、我们的产品…)发表意见,写在便利贴上贴成一面"产品愿景墙",最后把发散的意见收敛成统一语言。
看图抓什么:左边粉色那一列是一套填空模板(七个句式起头),右边黄色贴纸是团队填进去的答案。把图里这张"用户中台"的愿景墙填完后是这样的:
| 句式(粉色模板) | 团队填的答案(黄色贴纸) |
|---|---|
| 为了(谁) | 管理内部业务/运营类应用、外部 2B/2C 用户、用户登录岗位权限 |
| 他们的(诉求) | 通过接口获取用户权限(鉴权)、单点登录、资源的权限管理、统一用户信息服务、记录用户行为日志 |
| 这个(产品名) | 用户中台 |
| 是一个(定位) | 集中管理登录认证和权限的产品 |
| 它可以(能力) | 减少重复建设、实现单点登录、集团化运营、完成微服务之间授权 |
| 而不像(区别于现状) | 系统各自授权认证、4A 只负责登录认证 |
| 我们的产品(核心卖点) | 集中统一管理用户/权限/认证、覆盖范围广、可追溯的安全保障、多种登录方式(含生物识别)、高性能高稳定、灵活组合授权 |
💡 本质就是用一个结构化句式逼团队把"给谁用、解决什么诉求、是什么、凭什么比现状强"一次性对齐。填完连起来读就是一句完整的产品定位。注意这一步可以跳过:如果团队对产品愿景本来就清晰,不必走这个流程——它解决的是"人多嘴杂、方向没对齐"的问题。
第二步:业务场景分析——从用户视角遍历典型场景
场景分析站在用户视角,顺着业务流程 / 用户旅程,用用例和场景把领域里的典型场景都走一遍,从中挖出领域事件、实体、命令。原则:尽量遍历所有业务细节,别漏要点。
用户中台有三个典型场景:
| 场景 | 在干什么 |
|---|---|
| ① 系统和岗位设置 | 设置系统里岗位的菜单权限 |
| ② 用户权限配置 | 给用户建账户密码、设岗位 |
| ③ 登录与权限校验 | 用户登录系统、校验权限、生成日志 |
怎么挖?顺着流程找关键领域事件(如"岗位已创建"“用户已创建”),再倒推什么行为引起它——这些行为可能是一个或几个命令的组合。比如创建用户:命令1 是"从公司 HR 系统获取用户信息",命令2 是"根据 HR 员工信息在用户中台创建用户",做完就产生"用户已创建"这个领域事件。这个事件可能触发下一步(如发邮件通知),也可能到此为止——要具体分析。
看图抓什么:图横着分成三条泳道(对应上面三个场景),每条泳道又竖着分三行——命令(蓝)/ 业务流 / 事件(橙)。读法是从左到右顺着业务流走,看每一步发了什么蓝色命令、落下什么橙色事件。把图里三条泳道的真实内容抄出来对着看:
| 泳道 | 蓝色命令(从左到右) | 橙色事件(结果) |
|---|---|---|
| ① 岗位配置 | 创建系统 → 导入菜单清单 → 选择系统/选择菜单/系统菜单组合 → 创建岗位 | 系统已创建 → 菜单已创建 → 岗位已创建 |
| ② 用户权限配置 | 从 HR 中获取用户 → 创建用户 → 查询账户/创建账户/设置账户密码 → 分配岗位 | 用户已创建 → 账号已设置/密码已设置 → 岗位已分配 →(黄贴:邮件系统发送通知) |
| ③ 登录和权限校验 | 用户登录 → 查询用户 → 校验账户密码/校验 Token → 生成 Token → 获取权限/校验 API 权限 | 用户已登录 → 用户操作日志已生成 |
💡 注意第 ② 条里"邮件系统发送通知"是一张黄色补充贴——它提示"用户已创建"这个事件可能触发一个外部依赖(邮件系统),但邮件本身不是用户中台要建的领域对象。这正是黄色贴纸的用途:标注外部依赖和注意事项,不参与建模主体。
🪞 辅助理解(泳道怎么读):把每条泳道想成一条流水线传送带。蓝贴是"工人按下的按钮"(命令),橙贴是"机器吐出来的成品"(事件),中间的业务流是传送带方向。这一步先不管哪个工人、哪台机器(不归类实体),只把"按了哪些按钮、出了哪些成品"沿着传送带铺满整面墙。
🪞 场景分析 vs 愿景:愿景是"我们要造一栋什么样的楼"(方向),场景分析是"住进去的人每天怎么走动、开哪些门"(具体动线)。后者才能暴露出真正需要的房间(实体)和动作(命令)。
第三步:领域建模——把零散对象拼成模型(三小步)
这是最关键的一步:根据上一步产生的命令、事件,找实体 → 组聚合 → 划限界上下文,建起领域模型。模型向上靠限界上下文指导微服务设计,向下靠聚合指导聚合根、实体、值对象的设计。
小步 1:从命令和事件里提取实体(绿色贴纸)
分析用户中台所有的命令和事件,扒出产生这些行为的实体。最终提取出 7 个实体:用户、账户、认证票据、系统、菜单、岗位、用户日志。
看图抓什么:图里每一组都是 左边一堆蓝色命令 → 中间一块绿色实体 → 右边一堆橙色事件。读法很统一:绿色块是主角(实体),它左边挂着"它能被下哪些命令",右边挂着"它会产生哪些事件"。这一步就是把上一步满墙散落的蓝贴橙贴,按"这事儿是围着谁转的"归拢到 7 个绿色实体名下。把图里 7 个实体各自挂的贴纸抄出来:
| 绿色实体 | 左侧挂的命令(蓝) | 右侧产生的事件(橙) |
|---|---|---|
| 用户 | 从 HR 中获取用户、用户登录、获取账户、创建用户、查询用户、分配岗位、获取用户权限 | 用户已创建、岗位已分配、用户已登录 |
| 账户 | 创建账户、设置账户密码、校验账户密码 | 账号已设置、密码已设置 |
| 认证票据 | 生成 Token、校验 Token | (Token 相关,图中事件未单独标) |
| 系统 | 创建系统、查询系统 | 系统已创建 |
| 菜单 | 导入菜单清单、创建系统菜单、查询菜单 | 菜单已创建 |
| 岗位 | 系统和菜单组合、生成菜单、校验 API 权限 | 岗位已创建 |
| 用户日志 | 写入日志、查询日志 | 用户操作日志已生成、用户登录日志已生成 |
💡 怎么判断一张贴纸该归到哪个实体?看这张贴纸主要在操作/改变谁。"设置账户密码"改的是账户 → 归账户;"分配岗位"虽然带"岗位"两字,但它是把岗位分给用户、改的是用户的状态 → 归用户。这种"看动作落在谁身上"的判断,就是从命令/事件反推实体的核心手感。
🪞 提实体像整理购物小票:上一步铺满墙的命令和事件,像一地散落的购物小票。提实体就是按"这笔花在谁身上"归类:买猫粮、铲屎、看病 → 都归到"猫"这个主体名下。归完你就发现,原来这一摊事其实只围着 7 个主体转。
小步 2:找聚合根、组聚合
按"谁管谁"的性质从 7 个实体里挑出聚合根,再按业务依赖 + 业务内聚原则把聚合根和它关联的实体/值对象组成聚合。7 个实体最终收拢成 6 个聚合:
| 聚合 | 由哪些实体组成 | 说明 |
|---|---|---|
| 系统功能 | 系统 + 菜单 | 两个实体合成一个聚合(详见下方 💡) |
| 岗位 | 岗位 | 单实体成聚合 |
| 用户信息 | 用户 | 用户基本信息 |
| 用户日志 | 用户日志 | 登录/操作日志 |
| 账户 | 账户 | 账号、密码 |
| 认证票据 | 认证票据 | Token 等 |
💡 注意只有"系统"和"菜单"两个实体被合并成了"系统功能"一个聚合,其余 5 个实体各自独立成聚合。为什么偏偏这俩合并?因为菜单永远依附于某个系统、要跟着系统一起增删改,业务上强绑定。这正是聚合的意义:把"必须一起变、要保证一致"的东西打包成一个一致性边界,对外当一个整体(回忆 05 讲:聚合是数据修改和持久化的最小单位)。
小步 3:划限界上下文
按上下文语义把 6 个聚合归类成 3 个限界上下文:
| 限界上下文 | 包含的聚合 | 负责什么 |
|---|---|---|
| 用户信息 | 用户信息 + 用户日志 | 用户基本信息、登录/操作日志 |
| 认证 | 账户 + 认证票据 | 不同方式的登录与认证 |
| 权限 | 系统功能 + 岗位 | 系统/菜单管理、岗位配置 |
看图抓什么:整个用户中台是一个大椭圆(= 用户中台这个领域),里面用两条虚线切成三瓣,每瓣是一个限界上下文,瓣里装着橙色的聚合:
- 左上瓣【权限】:装着「系统功能」和「岗位」两个聚合——注意"系统功能"这个橙色聚合里,还嵌着系统、菜单两个绿色小方块(就是上一步合并进来的两个实体)。
- 右上瓣【认证】:装着「账户」和「认证票据」两个聚合。
- 下方大瓣【用户信息】:装着「用户信息」和「用户日志」两个聚合。
💡 这张图把三层结构一次性画全了:领域(大椭圆)→ 限界上下文(虚线分出的瓣)→ 聚合(橙色椭圆)→ 实体(绿色方块)。从外到里正好对应"作用范围从大到小"。虚线就是边界,它直接决定了将来微服务大概在哪儿切——到这一步,用户中台的领域模型就建完了。
🪞 限界上下文像把东西分进抽屉:6 个聚合好比 6 样工具,限界上下文就是 3 个抽屉。把"系统功能、岗位"放进【权限】抽屉,"账户、认证票据"放进【认证】抽屉,“用户信息、用户日志"放进【用户信息】抽屉。分抽屉的依据是"语义上是不是一类事”——而每个抽屉,未来很可能就是一个独立的微服务。
由于建模过程产生的领域对象太多,作者建议用表格把它们一条条记下来,方便归档和落地:
看图抓什么:表头五列——业务域 → 领域模型 → 聚合 → 领域对象 → 领域类型,从粗到细一层层往下记。拿图里截的片段感受一下填法(业务域都是"用户"、领域模型都是"用户信息"):
| 业务域 | 领域模型 | 聚合 | 领域对象 | 领域类型 |
|---|---|---|---|---|
| 用户 | 用户信息 | 用户信息 | 用户 | 聚合根 |
| 用户 | 用户信息 | 用户信息 | 创建用户 | 命令 |
| 用户 | 用户信息 | 用户信息 | …… | 命令 |
| 用户 | 用户信息 | 用户日志 | 日志 | 聚合根 |
| 用户 | 用户信息 | 用户日志 | 创建日志 | 命令 |
💡 重点看最右列"领域类型":它给每个对象贴上身份标签——是聚合根、实体、值对象,还是命令、事件。一个聚合里有且只有一个聚合根(如"用户信息"聚合里聚合根是"用户"),其余都是挂在它名下的命令/事件/子实体。这张表是领域模型的文字版台账:墙上的便利贴会撤、会掉,但这张表不会丢——它才是能正式交给开发(或喂给 AI)去落地代码的产物。前面那些彩色墙图是"过程",这张表是"交付物"。
第四步:微服务拆分与设计——领域模型只是"重要依据",不是"唯一标准"
原则上"一个领域模型 = 一个微服务",但作者特意泼了盆冷水:领域建模时只考虑了业务因素,没考虑落地时的技术、团队、运行环境等非业务因素。所以拆微服务时,领域模型只能当重要依据,不能当唯一标准。
除了业务职责单一,拆微服务还要权衡这些非业务因素:
| 维度 | 要考虑什么 |
|---|---|
| 服务粒度 | 拆多细、合多粗 |
| 敏态 vs 稳态 | 变化快的业务和稳定的业务要分离 |
| 非功能性需求 | 弹性伸缩、安全性等要求 |
| 团队组织 | 团队规模、沟通效率(康威定律) |
| 工程因素 | 软件包大小、技术异构 |
举个例子:用户中台不考虑非业务因素时,可直接按领域模型拆成用户、认证、权限三个微服务。但如果用户日志数据量巨大、大到得上大数据技术——那"用户信息聚合"和"用户日志聚合"就出现了技术异构:虽然建模时它俩在同一个领域模型里,但这时不适合塞进同一个微服务了。于是以聚合为单位,把"用户基本信息"和"用户日志"拆成两个用不同技术实现的微服务。
💡 关键认知:聚合是微服务拆分/重构的最小单位。领域建模给你画好了"业务上的理想切法",但真到工程上,技术、数据量、团队这些现实因素会让你在聚合的颗粒度上再切一刀或再合一块。
总结
事件风暴是一种和传统需求分析、系统设计很不一样的建模方法:不是一个人画图,而是领域专家 + 全团队围着一面墙、用彩色便利贴边吵边贴,从"领域事件"倒推出命令、实体,再归并出聚合和限界上下文。
落地分四步:① 产品愿景(对齐方向,团队若已清晰可跳过)→ ② 业务场景分析(站用户视角遍历场景,铺出"命令→事件"的因果链)→ ③ 领域建模(提实体 → 组聚合 → 划限界上下文,最后用表格登记台账)→ ④ 微服务拆分(领域模型是重要依据但非唯一标准,还要叠加技术异构、安全、团队等非业务因素,必要时以聚合为单位再切分)。
作者最后敲了两记重点:一是领域建模值得花时间(中型项目约两周,和传统需求分析差不多,但换来了全员通用语言);二是别跳过战略设计直奔战术——很多人学 DDD 只想学战术、快速撸微服务,这是误解。先有边界清晰的领域模型,才有边界清晰的微服务,这两步一前一后是刚需。
一句话速记
事件风暴 = 一群人围墙用彩色便利贴破案:从橙色"事件"倒推蓝色"命令"和绿色"实体",再拼成聚合、切成限界上下文;四步走(愿景→场景→建模→拆服务),领域模型定业务边界、聚合定微服务的最小切割单位,但落地还得叠上技术与安全这些现实账。
思考题
原题是"找个你擅长的领域,用事件风暴建一次模型"。挑一个你天天在用、闭着眼都熟的小系统练手——比如点外卖、个人记账 App、或一个读书笔记应用,按下面三步走一遍(全程别写代码):
- 当一回领域专家,从"事件"倒推:把这个系统里所有"……已发生"的领域事件先列出来(点外卖如"订单已提交"“骑手已接单”“餐已送达”“订单已评价”)。再对每个事件倒推:是什么命令触发了它?这个命令落在哪个实体身上?体会一下这种"先有结果、再找原因"的反向思维。
- 试着归拢和切块:把命令/事件按"围着谁转"归到几个实体上,再想想哪些实体该打包成一个聚合(比如"订单"和"订单项"要不要一起?),最后按语义把聚合分进 2-3 个限界上下文(如"下单"“配送”"评价"该不该各成一块?)。
- 整理出台账表,再喂给 AI:把建好的模型整理成那张"业务域 / 聚合 / 领域对象 / 领域类型"的台账表,然后拿它当 prompt 让 AI 生成代码。对比一下——有台账约束 vs 直接说"帮我写个外卖点单系统",AI 产出的代码在边界清晰度上差多少?这会让你直观感受到"为什么 DDD 要先建模、再写码"。






