我不是什么理论派diagram-design 这个项目就是我从一线摸爬滚打里总结出来的一套方法论和实践合集怎么把一张张技术架构图、流程图、部署拓扑图画得又快又清晰画完以后还好维护、好协作、能在团队里形成统一输出的完整套路。说直白点这是一套关于如何设计图表本身的设计规范不绑定某个具体工具但会配套讲清楚我用了什么工具链、为什么选它、踩过哪些坑。这篇文章就是把这个项目里沉淀下来的东西做一次完整的公开复盘适合日常要画架构图、写技术方案、做团队知识沉淀的研发和运维同学。无论你现在是画图全靠拖拽、还是导图做成一张没人能懂的巨型蜘蛛网看完你应该都能形成一套自己的出图逻辑。1. 为什么我要专门折腾一套“图表设计”的工程化方案1.1 画图这件事真的不只是画而已我刚开始带项目那几年最痛苦的事情之一就是看团队里面的各种图。技术方案 PPT 里贴出来的架构图有人用 Visio、有人用 ProcessOn、有人用 draw.io甚至还有人手绘拍照放进文档里。形式上五花八门也就算了关键是每张图的设计逻辑完全不同。同样一个服务调用关系在一些图里从上往下画另一些图里从左往右画同一个名词有人写订单服务有人写OrderService还有人写订单中心。当时每次评审会一半时间不是在讨论方案本身而是在帮大家理解这张图画的是什么。这就非常离谱图是拿来降低沟通成本的结果还在增加沟通负担。所以我做 diagram-design 这个项目第一个出发点非常朴素我们要在团队内部甚至跨团队之间形成一套关于图表的通用语言。包括图的类型、方向、命名、配色、元素关系表达方式全都约定成文。这样一来评审会上所有人打开同一张图视线停留的位置和读图的路径基本一致讨论直接进入正题。1.2 技术图的本质一次性的表达工具还是长期资产大多数人的误区是把技术图当成一次性的表达工具——方案评审会开完图的任务就结束了。但真正落地过系统的人会明白架构图、流程图、部署拓扑图这些东西生命周期远比你想象的长。我记得有一次做一个老系统的交接当时接手同学第一个问题就是有没有系统架构图。结果我们翻遍 Wiki 只找到一张三年半之前的截图还是 JPEG 格式画的范围跟现在的系统已经对不上了。后来没办法只能对着代码重新理解系统前前后后花了两周才把整体关系摸清楚。如果当初的那张图是一个可维护的源文件改起来可能只需要半天。这就是我把 diagram-design 当做一个项目来做的原因技术图不是用完即弃的草图必须把它当作一种长期维护的技术资产来设计。既然是长期资产就必须有工程化的管理方式——版本控制、变更记录、可复用组件、统一的风格规范缺一不可。1.3 市面上工具很多但缺少的是一套完整的设计方法平心而论绘图工具从来都不是瓶颈。draw.io 免费、ProcessOn 协作方便、Excalidraw 手绘感强、Figma 精致还有 Mermaid、PlantUML 这类代码化工具选择太多了。但工具多恰恰带来了缺乏统一方法的混乱。很多人换一个工具就换一套画图习惯在 A 工具里知道用分层、用泳道表达职责换到 B 工具里就全变成一个个孤立的框和箭头完全看不出来层级和归属关系。这就好比一个人换了台电脑就不会写代码了一样荒谬。tool从来都是画图里最简单的一环真正难的是脑子里有没有一套设计方法。diagram-design 的核心就是把技术图该怎么设计这件事给捋清楚一张图里有哪些基本元素、这些元素之间的关系如何表达、选什么布局、分几层、用什么颜色、线型和箭头怎么约定全都有明确原则可依。有了这套方法用任何工具画出来都不会差太多。2. 工具选型代码化绘图和拖拽式绘图怎么选2.1 两种路线各自的适用场景在做 diagram-design 这个项目的过程中我比较早做的一个决策就是工具分层绝不指望一个工具通吃所有场景而是根据图的类型、使用频率、维护周期选择不同层级的工具。第一类是高频率、需要持续维护的技术图典型代表是系统架构图、部署拓扑图、核心业务流程图。这类图我强烈推荐使用代码化绘图方案比如 Mermaid、PlantUML或者 Python 的 Diagrams、Graphviz。代码化最大的优势在于图本身就是文本能像代码一样进 Gitdiff 出来清清楚楚这周改成什么样、为什么改全都有记录。而且用代码画的好处是——你不需要手动调整每一个框的位置引擎会根据结构自动决定排布这天然地促使你去思考逻辑关系而不是把所有精力花在拉对齐上面。第二类是低频的、仅供讨论的草图典型场景是白板上的方案推导、即时聊天里随手画一个流程。这种图用 Excalidraw、或者直接纸笔画都行追求的是快速表达不需要考虑长期维护。需要注意的是这种一次性草图最好在真正拍板后抽时间转成第一类正式图纳入资产库否则又会陷入前面说过的无图可查的困境。2.2 我最终在项目里沉淀的核心工具链结合通用性、可维护性、上手曲线三个维度我在项目里沉淀了一套组合拳场景首选工具备选方案选择理由架构图 / 部署图Python DiagramsPlantUML代码化、自动布局、支持云服务图标时序图 / 状态图PlantUMLMermaid时序图和状态图的表达力强常规流程图Mermaiddraw.io语法简单GitHub/Wiki 原生支持快速讨论草图Excalidrawdraw.io上手零门槛、实时协作正式的方案文档配图draw.io手动整理Figma精确控制布局、视觉风格统一这套组合用下来我个人的体感是80% 的技术图用代码化工具画效率高、可维护性强剩下 20% 需要精细排版、面向外部汇报的图再手动拖拽整理能同时兼顾效率和质量。2.3 补充一个很多人忽略的维度兼容团队现有协作生态选工具的时候光看自己用着顺不顺是不够的还得看团队现有的协作生态。打个比方你们团队代码托管在 GitLab 上文档用 Confluence那 Mermaid 一定是比什么都合适的选择因为 GitLab 和 Confluence 对 Mermaid 的渲染支持都已经很成熟了写完代码直接嵌入文档所见即所得。我自己就遇到过一次教训当时我给团队引入了某个著名的在线绘图工具功能确实很强但后来发现它跟公司内部知识库系统没有集成每次文档里要嵌入图片还得先导出上传而且图片更新了旧文档里不会自动同步。后来整个项目组的图慢慢就都过期了等于白干。所以工具选型不只看工具本身还要看它能不能嵌到团队已有的知识流转链路里去。3. 可落地的图表设计规范布局、命名、配色、层级3.1 布局方向先想清楚读者怎么读图很多人的图画得乱根源不在于线条画得歪而在于布局方向没想清楚。技术图本质上是一个叙事过程读者看图是有顺序的设计师要把这个顺序安排好。我的核心规范是业务流和数据流优先从上到下架构组成关系优先从左到右。为什么这么定因为我们的阅读习惯决定了这种方向最自然。上到下的流程符合时间推进的直觉比如用户从下单到支付再到出库左到右的架构符合层级构成的表达比如接入层在左、应用层在中间、数据层在右。还有一个布局原则是减少交叉。如果发现图里的线交叉超过三个那一定不是线的问题是布局方式错了。这时候我会尝试调整节点的排列顺序或者干脆把一张复杂的图拆成两张。交叉线是读图最大的干扰因子一张图若需要读者沿着某条线来回找关系那这张图的设计就是失败的。3.2 命名规范一图一术语全图同名词命名看起来是小事但却是技术图设计中最影响专业度的一环。我见过太多图里出现同一个概念多种叫法的场景读者就会陷入这个和那个是不是一个东西的疑惑中。所以我定了三条硬性规范概念命名以需求文档和代码中的正式命名为准禁止在图上自创简写中英文命名二选一选定后全图统一不允许混用图内所有节点名称必须唯一多实例节点用序号区分这里举个例子假设有一个用户服务代码里叫user-service那么在架构图上就统一写用户服务user-service后面所有图、所有文档都沿用这个称呼不许某张图里又冒出来一个用户中心。别小看这个一致性约束它带来的沟通效率提升是肉眼可见的。3.3 配色原则克制是最大的专业技术图配色可能是最容易被忽略、也最容易翻车的地方。很多新手容易犯的毛病是觉得图要好看就上各种高饱和度的颜色结果整张图花里胡哨重点反而被淹没。我沉淀的配色原则其实就三句话一图不超过五种颜色同一层级用一种色系关键路径用高亮度强调。具体实践是这样架构图里所有应用服务用一种主色中间件用一种主色数据存储用一种主色外部调用用一种主色基础底座用一种主色——各司其职绝不会在同一层里一会儿蓝一会儿绿制造混乱感。需要强调的重点节点比如这次改造新加的服务就在主色基础上提高一档亮度或者加粗描边。色弱读者能区分、灰度打印也不至于完全失去辨别度这才是好的配色。3.4 元素表达方框、圆角框、虚线、实线不能乱用diagram-design 里对基本元素有一套成文的语义约定我在这里完整列出来可以直接抄作业元素语义使用场景实线矩形系统/服务/模块可独立部署或运行的组件圆角矩形逻辑概念/聚合业务域、限界上下文、功能模块虚线边框外部依赖/可选组件第三方服务、待建设模块实线箭头同步调用/强依赖RPC、HTTP 接口调用虚线箭头异步通知/弱依赖消息队列、事件订阅线条粗细依赖强度粗线为主链路细线为辅助链路这套约定看起来简单但实际用起来效果极好。有一次评审方案我看到对方的流程图里同步和异步调用画得完全一样就提醒了一句同步用实线、异步用虚线不是画图工具的问题是设计表达的问题。改用这套语义后消息驱动的系统那张图瞬间清晰了很多——哪里等结果、哪里不等结果一眼就能分辨。4. 实操案例一个微服务系统架构图的设计全过程4.1 需求场景与绘图目标为了让你更直观地理解整套方法长什么样我拿一个真实的例子走一遍流程。这次要服务的场景是公司内部的一个电商后台系统需要做技术架构图的整体升级服务于三个目标——新同学入职快速了解全局、技术方案评审画改造范围、日常运维排查问题时对照拓扑。这个场景决定了我画图的取舍方向要中粒度的全局图不是代码级细粒度要标注清楚服务间依赖关系要能看清楚链路的关键路径也要能体现系统的分组和层级归属。4.2 设计过程从信息收集到草图第一步收集信息。我梳理了线上实际运行的进程列表、服务注册中心的实例清单、网关的路由配置、消息队列的 Topic 清单。这项工作务必基于实际运行配置来做而不是凭记忆。有一次我对照一个旧架构图画新的演进方案结果旧图画漏了一个做数据同步的 Worker 服务导致方案评审的时候被运维同事当场指出场面一度非常尴尬。第二步分组聚类。我把几十个服务按照职责分成四个组接入网关层、业务应用层、消息异步层、数据存储层。分组是整个设计中最关键的一步分组对了后面布局和连线就顺理成章。分组的判断标准是变更的关联度哪些服务经常会一起改动就把它们放在相邻位置。第三步画出草图。这里我用的是 python 的 Diagrams 库代码结构大概是这样from diagrams import Diagram, Edge, Cluster from diagrams.aws.network import APIGateway from diagrams.programming.language import Python from diagrams.onprem.queue import Kafka from diagrams.onprem.database import PostgreSQL from diagrams.onprem.container import Docker with Diagram(电商后台核心架构, showFalse, directionTB, filenameorder_arch): gateway APIGateway(API 网关) with Cluster(业务应用层): order_svc Python(订单服务) user_svc Python(用户服务) payment_svc Python(支付服务) with Cluster(消息异步层): mq Kafka(订单事件总线) with Cluster(数据存储层): db PostgreSQL(业务主库) dw PostgreSQL(分析库) gateway order_svc gateway user_svc order_svc mq user_svc db payment_svc db mq dw这里有几个细节值得说一下。directionTB表示从上到下布局这是我在前面规范里定的业务流和数据流优先从上到下落地方式。用 Cluster 来天然表达分组这样视觉上面向组的概念非常清晰。文件名我直接命名为order_arch后面维护时配合版本注释一眼就能看明白这张图是干什么的、包含什么层级。4.3 生成与优化不是画完就结束草图生成出来后我先检查一遍连线关系然后把它截图发到项目群请后端、运维、前端同事都帮忙找茬。这一环节特别重要因为你永远不是对系统最熟的那个人群策群力能挖掘出很多平时注意不到的隐藏依赖。第一轮反馈确实提了不少有效问题比如订单服务还有一个定时任务在跑关单逻辑图上没体现支付回调是通过消息异步触发的图上画成了同步调用等等。我根据反馈在原代码基础上修改加了定时任务节点把支付回调改成虚线箭头。改完之后重新生成图就比第一版准确、也清晰了很多。最终成图的时候我还会再做一次陌生度测试拿给一个对公司系统不熟的同事看让他不提问地说说自己的理解。如果他能讲个七七八八说明这张图的表达已经合格了。如果不合格我就再调整布局和命名直到不解释也能看懂为目标。这个测试费不了多少时间但能极大地提升技术图的通用表达能力。4.4 迭代与维护把图当成代码来管图生成之后我不允许它继续停留在 PG 一张静态图的地步。我的做法是把这个order_arch.py文件放进代码仓库的一个docs/diagrams目录下并在 README 里写明如何重新生成图片、更新时要注意什么。后续每当系统架构发生变更相关 MR 必须同步更新对应的图源码。这里顺便说一个我踩过的坑很多人喜欢在 draw.io 这类工具里直接改图但改完之后源文件是.drawio后缀的 XML 文件没法很好地做 diff审查的人很难快速看出结构变化。而用代码化方案比如 Python Diagrams 或 PlantUML每次变更是哪一行依赖关系变了一眼就能看出来。这从工程管理的角度来讲是压倒性的优势。5. 设计技术图时候的几个关键检查项5.1 这张图能不能脱离作者而独立存活画图的时候我经常心里会过一遍一句话如果我不在这个公司了这张图还能不能被人看懂。这不是自嘲而是最真实的设计底线。检查方法也很简单把图发给一个上下文一无所知的人看观察他需要提问几次才能明白图里的核心关系。提问次数越多说明图的自解释能力越差。导致自解释能力差的原因通常有三个大量使用不规范的缩写、节点之间没有明确的分组层级、线型箭头语义混乱。这三件事做好了至少能覆盖 80% 的烂图问题。5.2 这张图是否可以直接拿来评审评审场景对技术图有两个额外要求一是改造范围必须一目了然二是变更链路上的影响点必须显式标注。这种情况我通常会在图里用红色或者高亮描边标出新增节点用虚线框标出待下线节点用加粗箭头标出本次变更涉及的主链路。有了这套标注评审会的时候就不用反复说大家注意这块这里有个隐藏关联图自己就会说话。省下来的沟通时间都变成了方案讨论的有效时间。长期下来整个团队的技术评审效率都会有非常明显的提升。5.3 一图与多图的分工是否清晰技术图的另一个常见困境是什么都要画进一张图里。系统规模一大一张架构图里又画部署拓扑、又画数据流、又画模块依赖最终只能是一张谁都看不懂的蜘蛛网。最合理的做法其实是一图一主题。我的划分习惯是这样有宏观全局架构图把所有服务和分组都列出来连线只画核心依赖有专项链路图比如订单创建链路只画经过的五个节点和它们之间的调用有部署拓扑图专门画机房、集群、容器、存储的分布式关系。每张图只讲好一件事但通过标题、标签互相引用形成一个图件体系比一张无敌大图实在得多。6. 常见问题与排查技巧实录6.1 图里的线交叉太多怎么处理交叉线是技术图设计里最让人头疼的问题没有之一。我用 Python Diagrams 这类自动布局工具生成的图也偶尔会出现线交叉。排查的时候遵循一个顺序先看分组是否合理再看节点排列顺序最后考虑拆分。一个很实用的技巧是把高频交互的节点尽量放在同一组或相邻位置。比如订单服务和支付服务如果交互频繁就把它们排在一起中间不要隔着一个完全不相关的用户服务。如果调整完还是交叉严重那就果断把这张图拆成两张——一张强调依赖关系一张强调调用顺序。拆图没有任何羞耻感能讲清楚问题才是核心目标。6.2 中文内容在代码化绘图里显示乱码用 PlantUML 和 Python Diagrams 画图时中文乱码是新手绝对会遇到的第一个问题。PlantUML 需要指定支持中文的字体并且要保证环境里装了对应的中文字体文件Python Diagrams 内部走 Graphviz 渲染也需要设置中文字体。我踩过这个坑之后的标准化操作是在 Graphviz 的配置文件里统一设置fontname Microsoft YaHei或者PingFang SC确保服务器和本地环境的字体一致。另外注意一点不同操作系统上的中文字体名称不一样跨平台协作时最好在代码里检测系统类型后再动态设置字体否则同一个源文件你电脑上生成正常同事 Mac 上生成就是方框。这种问题一旦出现排查起来挺费时间不如提前约定好环境。6.3 图规模一大渲染就很慢当图的节点数量超过 50 个、关系超过 100 条的时候某些代码化绘图工具会出现渲染变慢、布局不可控的问题。我在项目里遇到过几次情况是 Mermaid 生成大型流程图时浏览器直接卡死等了半天只看到一个不停转的加载圈。后来我的解决策略是大图变小图。宏观架构图只保留服务级别的节点去掉类和代码方法级别的细节链路专项图只画涉及该链路的节点不带无关组件。如果确实需要展示完整的宏观拓扑我会把图拆成多个子图在文章里用文字说明子图 A 和子图 B 之间的关系是什么而不是硬要靠一张图装下整个世界。这背后的根本原则是技术图的表达容量是有边界的一定要在设计阶段就意识到这张图不该画什么比该画什么更重要。6.4 团队多人协作维护同一张图怎么避免冲突代码化图的好处是天然适合协作因为它是纯文本。但多人维护同一个文件的时候如果没有约定冲突同样是家常便饭。我定的协作规范是一个图文件原则上只有一个 owner由他负责合并其他人的变更建议其他人如果要改图优先通过提 issue 或者评论里描述修改点的方式而不是直接改文件。如果必须要多人同时修改我会把大的架构图按子系统拆成多个源文件然后在文档页面里组合引用。这样每个人改自己负责的那一块互相之间不受影响。用 Git 管理的时候改了什么一目了然review 起来也就顺理成章了。7. 最后分享两个我在反复实践中沉淀下来的小技巧第一个技巧画图前先写好一句话说明。不管你用任何工具动笔之前先用一句完整的话写下这张图的核心表达例如这张图展示用户从登录到下单完成的全过程然后所有设计都服务于这句话。如果画着画着发现某个元素跟这句话无关果断删掉。别觉得可惜图的质量往往和信息克制呈正相关。第二个技巧每次成图后顺手记录一下这张图已经过时了的检测方法。比如架构图我会在注释里写清楚判断此图是否过时看服务注册中心里名为 order-service 的应用实例数量是否与图保持一致。这个方法听起来笨但非常有效能快速判断一张存量图的可信度。diagram-design 这个项目做到现在我最深的体会是画图本质上是梳理思考的过程图纸只是载体。当你养成了先分层、再命名、后连线、最后审视的习惯任何工具在你手里都能画出让人一眼看懂的技术图。希望这篇文章里沉淀的方法和规范能帮你在下一次画图的时候少走几步弯路。