ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

技术方案怎么画好三张大图?架构图、流程图、时序图实战指南

技术方案怎么画好三张大图?架构图、流程图、时序图实战指南 技术方案的评审效率往往不取决于你写了多少字而取决于对方看到了什么。很多开发同学都有过类似经历花了两天写完一份设计稿逻辑、流程、接口定义都写得清清楚楚结果评审会上大家还是对着同一段文字反复确认“这里是谁调用谁”“这条链路失败以后去哪里”。问题不在文字质量而在信息呈现方式——文字是线性阅读图是结构阅读人在看方案时图的处理速度远快于文字。所以每次写稿件、写方案、写技术博客我都有一个习惯先确定三张最核心的大图再围绕它们补充文字。这就是“3张大头”的意思——不是标题党而是指一份技术交付物里最有价值的三个图形资产。这篇稿子不讨论泛泛的“如何画图”而是把问题收敛到具体的场景一份技术方案、一篇技术博客、一次架构评审最值得花精力打磨的三张图是哪三张分别怎么画用什么工具画画完如何维护、如何嵌入文档、如何避免评审时被追问到说不清。读完之后你可以直接拿自己手头一份旧方案练手把它重构成“三张大图 精简文字”的结构再对比一下评审体验。1. 为什么方案评审总在“看不懂”上翻车先还原一个非常常见的场景。你打开一份设计文档看到一大段文字“用户请求先经过网关进行鉴权鉴权通过后由订单服务处理订单服务首先查询本地缓存如果缓存未命中则回源到数据库同时将结果写回缓存随后订单服务调用库存服务扣减库存扣减成功后返回结果如果库存不足则抛出异常……”这段话信息量很大但绝大多数人读完一遍是记不住完整链路的必须在脑中重新组织出一条分支图才能判断逻辑是否正确。问题出在认知负担上。文字是一种线性编码阅读者必须逐行处理再自己建立节点之间的连接关系。而图直接把节点和连接呈现出来阅读者只需要做一件事沿着箭头走。对于包含分支、依赖、多参与者协作的内容图的信息密度和处理效率远超文字。更隐蔽的问题是评审时每个人的关注点不同。有的人关心边界划分有的人关心异常分支有的人关心调用依赖。一段纯文字很难同时满足所有视角。而一张架构图可以让人快速找到自己关心的模块一张流程图可以让人快速验证主链路一张时序图可以让人快速对齐交互顺序。不是文字没用而是文字适合承载细节图适合承载结构。所以这里给一个明确判断技术稿件的说服力峰值出现在结构清晰的大图上而不是出现在洋洋洒洒的章节里。与其花时间扩充文字不如先把图打磨到能让一个不了解背景的人在三分钟内读懂。对比维度纯文字方案三张大图 文字方案阅读方式线性逐行理解先整体后细节可跳跃空降评审理解成本高需要脑内重建结构低图就是共享心智模型定位问题速度慢需要反复比对上下文快按图索骥会后被追问概率高容易忽略分支和边界明显降低维护成本低改一次文字即可略高需要同时维护图源文件2. “3张大头”到底是哪三张图架构图、流程图、时序图所谓三张大图不是随便选三张好看的图而是对应系统设计中最常被追问的三个问题系统由什么组成边界在哪里模块之间是什么关系一个业务目标是怎么被完成的主链路是什么有哪些分支和异常多个参与者之间如何协作谁先发消息谁等待谁消息顺序是什么第一个问题用架构图回答第二个问题用流程图回答第三个问题用时序图回答。这三张图分别覆盖了“组成、流程、协作”三个视角组合在一起基本就能支撑一份技术方案的主体结构。有些方案还会用到类图、ER图、部署图、状态图但那是领域深入后的补充。在“先把方案讲清楚”的阶段三张大图是最小必要集合。画好这三张云评审时的“看不懂”问题就解决了一大半。这里特别提醒一个误区很多人会画“伪架构图”就是网上常见的那种五颜六色、带渐变和卡通图标的示意图。这种图对PPT演示有用但对技术评审价值很低。技术评审里被追问得最多的往往是边界、依赖方向、数据流向这三件事如果图画得好看但说不清谁依赖谁评审成员还是会把问题抛回给你。图类型回答的问题核心要素适合场景架构图系统由哪些模块组成边界在哪模块、依赖、层次、外部系统方案概览、系统设计、团队对齐流程图一个任务按什么顺序执行节点、分支、判断、结束业务流程、请求链路、异常分支时序图多个对象之间如何交互参与者、生命线、消息、返回接口交互、异步消息、分布式事务3. 工具选型先想清楚图是否需要持续维护画图工具很多但如果要长期维护和进代码仓库工具选型建议先回答一个问题这幅图是一次性的还是会在版本迭代中持续修改如果是一次性示意图ProcessOn、draw.io、Excalidraw 这类图形化工具很合适拖拽快调整方便。但如果图会跟着代码一起变更更推荐用文本化绘图工具比如 PlantUML、Graphviz或者 Mermaid。原因很简单文本化图源可以进 Git 做 diff可以参与 Code Review可以写注释说明为什么这么连不会被“谁改了图导致对不上”的问题困扰。不过要注意一个现实问题不是所有 Markdown 平台都原生渲染这些文本绘图语言。CSDN 编辑器在部分环境下支持 Mermaid但为了在历史版本、各种浏览器和分享出去的文档里保持稳定更稳妥的做法是先渲染成图片再嵌入正文。文本化图源负责维护导出图片负责展示两条路径分层处理。具体版本号这里不写死因为这类工具迭代很快以各自官网最新版为准。文章后面所有示例用的都是 PlantUML 和 Graphviz 的通用语法在任何已安装环境中都能运行。工具选择建议如下场景推荐工具理由快速梳理思路Excalidraw、draw.io拖拽快适合草稿正式方案图PlantUML、Graphviz文本化可进Git可注释博客配图文本绘图后导出SVG/PNG可维护排版稳定团队协作高频修改PlantUML Git变更可追溯可评审4. 第一张大图架构图怎么画才能经得起追问架构图的本质是把系统的静态结构画清楚。它要回答的问题很朴素系统里有哪几个部署单元每个单元负责什么谁依赖谁数据流向哪里。画架构图第一步不是打开工具而是先确定边界。边界可以是逻辑边界比如订单服务、用户服务、库存服务也可以是物理边界比如网关层、应用层、数据层。对于中小型项目直接用逻辑边界分模块更直观对于复杂分布式系统建议从上往下分层接入层、业务层、基础设施层、外部依赖层。画的过程中最容易犯的错误是“什么都要放进来”。一张架构图只表达一个主题如果业务模块、部署机器、中间件、外部对接全部堆在一张图里很快会变成一团乱麻。更合理的做法是主架构图只画核心模块和依赖方向细节用局部图展开。下面用一个 Graphviz 示例说明如何表达模块依赖与层次关系。这里以 Spring Cloud 常见的“网关 → 服务 → 数据库”结构为例重点演示图的语法结构而不是绑定某个具体项目。// 文件路径docs/diagrams/architecture.dot digraph system { rankdirTB; node [shapebox, stylerounded, fontnameMicrosoft YaHei]; subgraph cluster_client { label客户端; styledashed; client [labelAPP / 浏览器]; } subgraph cluster_gateway { label接入层; gateway [labelAPI Gateway]; } subgraph cluster_service { label业务层; order [labelOrder Service]; stock [labelStock Service]; user [labelUser Service]; } subgraph cluster_data { label数据层; db [labelMySQL]; redis [labelRedis]; mq [labelMessage Queue]; } client - gateway [labelHTTPS]; gateway - order [label路由]; gateway - user [label路由]; order - stock [labelDubbo/HTTP]; order - redis [label缓存读写]; order - db [label持久化]; order - mq [label发送消息]; stock - db [label库存扣减]; }这段 dot 代码说明几个要点subgraph cluster_xxx用于在图中画出分组边框表达“层次”或者“域”的概念rankdirTB让图按从上到下的方向排列符合用户阅读习惯label写在边上用于表达依赖类型。渲染时架构图会按集群边界清晰分组比把所有节点平铺在一行更有层次感。Graphviz 渲染命令也很简单# 将 dot 源码导出为 SVG 文件 dot -Tsvg docs/diagrams/architecture.dot -o docs/diagrams/architecture.svg这里补充一个经验判断架构图是否合格可以拿三个问题来检验。第一每个矩形是否都能用一句话说清“它负责什么”第二任意两个模块之间的箭头方向是否和代码里的依赖方向一致第三如果删掉某一个节点图上的箭头是否还讲得通。三个问题都成立这张架构图就经得起评审追问。5. 第二张大图业务流程图怎么画才不漏分支流程图解决的是“任务怎么被完成”的问题。相比架构图的静态结构流程图更关注事件的推进顺序先做什么再做什么满足什么条件走哪条路失败在哪里终止或重试。画流程图的常见问题是不画异常分支。很多人的流程图只有主链路用户下单、库存扣减、发送消息、返回成功。一旦评审问“库存扣减失败怎么办”“消息发送失败怎么办”“重复请求怎么处理”图上一个节点都找不到又要临时补一段文字来描述。这种流程图在评审会上没有太大意义。更好的做法是画一张泳道图或活动图明确区分不同参与方的职责并把关键异常分支画出来。下面是 PlantUML 活动图的示例模拟一个最简单的下单流程重点在于展示if/else分支和repeat循环的表达方式。startuml start :用户发起下单请求; :网关鉴权; if (鉴权通过?) then (是) :创建订单; :调用库存服务扣减库存; if (库存充足?) then (是) :支付扣款; :发送消息通知; stop else (否) :标记库存不足; :返回失败原因; stop endif else (否) :返回未授权提示; stop endif enduml这段代码对应的逻辑是先判断鉴权再判断库存最后走支付与消息通知。PlantUML 的if (条件?) then (分支名)语法会把分支标签直接显示在判断节点上阅读者可以快速找到每条分支的走向。渲染命令同样很简单plantuml docs/diagrams/order-process.puml -tsvg画流程图的另一个建议是给每个判断节点加上“是/否”或具体条件标签不要只画一个菱形却不说明判断依据。比如“库存充足”比“库存状态”更容易被评审理解。分支条件是流程图的核心信息省略掉就等于没有画分支。此外流程图要控制单图规模。一个完整业务流程可能有上百个节点全部放在一张图里会丧失可读性。建议遵循“一张图只画一条主链路 关键分支”的原则把复杂的子流程独立成另一张图然后通过文字链接互相引用。这样做的好处是每一张图都能在几分钟内被人看懂而不是变成一张要缩放半天才能找到自己模块的蜘蛛网。6. 第三张大图时序图怎么画才能说清交互顺序架构图画了模块和连线流程图画了业务推进顺序但分布式场景下还有一个更棘手的问题多个模块之间的消息顺序到底是怎样的谁先启动谁等待谁谁异步处理失败后有没有补偿机制。回答这些问题需要时序图。时序图的核心元素是参与者和生命线。每一位参与者在图中表现为一条垂直虚线参与者之间的消息则用水平箭头表示。从上往下看箭头的先后顺序就是时间顺序。这个模型非常适合表达接口调用链、异步消息、分布式事务里的协商过程。下面用 PlantUML 时序图模拟一个分布式下单的交互过程。为了体现“接口调用 异步消息”两种交互模式示例里加入了消息队列这一参与者。startuml actor 用户 participant API Gateway as gw participant Order Service as order participant Stock Service as stock participant Message Queue as mq participant Notification Service as notify 用户 - gw: 提交订单 gw - order: 转发下单请求 order - order: 校验参数\n生成订单号 order - stock: 预扣库存 alt 库存充足 stock -- order: 预扣成功 order - mq: 发送下单完成消息 mq - notify: 异步消费消息 notify -- 用户: 推送通知 else 库存不足 stock -- order: 预扣失败 order -- 用户: 返回库存不足 end enduml这段代码展示了两个核心语法-表示同步消息--表示返回消息返回消息一般用虚线表达alt/else/end用于表达交互中的条件分支。在实际方案里存在多个分支时可以把所有分支画在一个alt块里让评审成员一眼看出不同情况下的消息差异。时序图的难点不是语法而是对象粒度。太粗的时序图画成“用户 → 系统 → 数据库”只有三条线漏掉了内部关键交互太细的时序图把每个 getter、setter 都画出来又失去表达力。一个合理的标准是只画“会产生业务后果”的消息比如状态变更、数据落库、消息发送、远程调用不画编程细节。画时序图前建议先做一件事把一次请求从头到尾的完整事件顺序写在纸上标出哪些事件是同步等待哪些是异步触发哪些失败后需要补偿。这个事件清单本身就是时序图的草稿。把事件序列理清楚后再画图画出来的时序图不会出现“消息顺序和代码实际执行顺序不一致”的硬伤。7. 把三张大图嵌入稿件和博客的规范做法图画完之后要把它们放入技术方案文档或 CSDN 博客时这里有几个值得长期坚持的习惯。第一尽量导出 SVG 而不是仅用 PNG。SVG 是矢量图在视网膜屏幕和各类浏览器下都能保持清晰用户放大看细节也不会糊。PNG 在部分老旧编辑器里兼容性更好但清晰度受限于导出时的分辨率。如果对清晰度要求高又不确定阅读设备建议 SVG 和 PNG 各导出一份文档里优先使用 SVG。第二图源文件和图片文件分开存放。一个推荐目录结构如下docs/ diagrams/ source/ architecture.dot order-process.puml order-interaction.puml images/ architecture.svg order-process.svg order-interaction.svg design/ order-design.mdsource 目录保存可编辑的文本源码images 目录保存渲染后的图片。这样既能在文档中稳定引用图片又能在后续修改时找到源头不会出现“图片过期但改不动”的局面。第三在 Markdown 文档中引用图片时路径要写成相对路径并给图片加上有意义的文件名。比如!-- 文件路径docs/design/order-design.md -- ## 下单流程设计 整体架构如下图 ![架构图](../diagrams/images/architecture.svg) 下单主链路如下 ![下单流程图](../diagrams/images/order-process.svg) 核心交互顺序如下 ![下单时序图](../diagrams/images/order-interaction.svg)在 CSDN 发布博客时图片会转存到平台图床。这里提醒一下上传后建议检查图片是否正常显示因为图床转存偶尔会出现样式丢失或链接过期的情况。如果博客里引用了多张图建议一次上传完成后预览全文确认图片顺序和文字描述一致。还有一个经常被忽略的细节图片命名。不要用1.png、2.png、未命名.png这种命名方式建议用“文档主题 图类型 序号”的格式。比如order-architecture-01.svg、order-flow-02.svg。这样别人下载图片后也能从文件名判断图片内容搜索引擎收录时也多了一份文字信息。8. 常见问题与排查方法写图和渲染图的过程中有几类问题出现频率很高整理成一张排查表方便直接对照处理。问题现象可能原因排查方式解决方案导出的图片中文字乱码渲染环境缺少中文字体或未指定字体查看渲染日志检查系统中文字体统一指定 Microsoft YaHei / Noto Sans CJK 等中文字体图片放大后模糊只导出 PNG 且分辨率过低查看图片实际像素换用 SVG或导出时提高 DPIPlantUML 渲染慢首次需要下载 jar 或依赖网络资源查看执行时间检查网络使用本地 CLI 或提前缓存依赖Graphviz 布局混乱、连线交叉多节点间没有合理分组或缺少约束观察连线关系和节点数量使用subgraph cluster分组用rank控制层级图源变更后文档图片未更新只改了源文件没重新渲染对比源文件和图片时间戳把渲染命令写进脚本或增加检查步骤多人协作修改图源冲突多个成员同时编辑同一份绘图文件查看 Git 冲突文件图源拆分为模块文件或约定变更窗口9. 最佳实践与工程建议三张大图只是起点真正决定长期价值的是围绕图建立起来的规范。下面几条经验是从多次评审实践中沉淀下来的适用于技术方案、团队文档和 CSDN 博客三类场景。第一一张图只表达一个主题。架构图就讲组成与依赖流程图就讲推进顺序时序图就讲跨对象交互。既有“画面的能力”还要有“不画什么的克制”。当一张图开始变得拥挤时不是继续往里填内容而是拆图。拆开的图可以用文字链接串联读者需要宏观视角就看主图需要细节就看局部图。第二图的变更要和代码变更一起评审。很多团队文档过期是因为“写完就没人维护”。如果用的是文本化图源可以把图渲染命令写进持续集成脚本或者在 MR/PR 模板里增加一项“本次变更是否涉及架构图/流程图/时序图更新”。这项检查能在代码评审阶段就发现文档需要同步修改避免图和代码分叉。第三评审方案时遵循“先看图后看字”的流程。技术评审的组织者可以先花两分钟让所有人独立阅读三张大图再进入提问和讨论环节。这样做的好处是让空降到项目的成员也能快速获得上下文。很多无效讨论都源于成员在脑内建立了不同的“图”而用统一的大图对齐视点能从源头上减少分歧。第四图的配色和风格尽量统一。不是为了好看而是为了降低阅读成本。比如统一用虚线表示异步或返回消息用实线表示同步调用用不同颜色区分外部依赖和内部模块用相同的字体和字号保证导出图片在文档中视觉一致。建议在团队内约定一套简单的绘图规范写入 README。第五涉及安全或合规信息的图要特殊处理。架构图通常会暴露内网拓扑、服务名、端口关系、中间件版本。公开发布博客或外部分享时要检查是否需要打码、替换服务名、去掉真实域名。内部文档和外部文档的图中内容可以不同不要图省事直接把内部图脱敏后发出去脱敏必须经过反复确认。第六画图工具本身不是重点可维护性才是。与其用最炫酷的工具画一张只能看不能改的图不如用大家都会的文本化方案画一张能持续维护的图。技术方案的价值在于它被一次次修改、应用、验证而不是一次性展示完就定格。10. 总结用三张大图重构你的下一份方案回到开头那个问题为什么很多方案评审“看不懂”因为文字只能线性描述结构而技术方案往往是个网状结构。三张大图的价值就是让你把网状信息转化为图形结构给评审者一个统一的心智模型。真正的交付标准应该是这样的一个人没有参加过你的项目但看完架构图能说出系统分了几层、核心服务有哪几个看完流程图能说出主链路和两个关键异常分支看完时序图能说出核心链路里哪一步是同步、哪一步是异步、失败后走什么分支。达到这个标准你的方案就已经成功了一大半。很难达到这个标准具体建议是把手头最近一篇旧方案翻出来试着只保留三张大图把文字压缩到图下方作为补充说明然后发给一个不了解项目的人看问他能否在三分钟内复述方案的核心结构。不能就继续改图能说明你已经掌握了这套方法。技术写作如此代码设计也是如此真正高效的信息传递永远是结构先于细节。所以下一次写方案时先把三张大图画出来。
返回列表