Skip to content

Mermaid 架构图语法实测:flowchart / architecture-beta / C4 / block-beta 怎么选 ​

Mermaid 不只是画流程图。11.x 版本里有好几种专门的架构图语法,但文档零散、中文资料少,而且各有各的解析脾气。

本文用同一个部署拓扑做横向对比。除了 architecture-beta(原因见第 3 节),其余语法都在本博客实际渲染通过;所有代码块都用 mermaid@11.16.1 校验过,解析失败的写法也一并列出并说明原因——这些坑不写出来,你照抄就会收获一个红色错误框。


1. 先看结论 ​

语法定位语义强度中文标题本站可渲染
flowchart通用流程图,什么都能画弱(只有连线)✅ 直接写✅
architecture-beta云/服务架构图,有分组与方位概念中⚠️ 必须加双引号❌ 见第 3 节
C4Context / C4ContainerC4 模型,人/系统/容器分层强(区分角色)✅ 直接写✅
block-beta块状栅格布局,接近系统框图弱✅ 直接写✅

一句话选型:要语义、给人讲架构 → C4;只是想连线 → flowchart;想摆成方块矩阵 → block-beta。(architecture-beta 语法本身不错,但在本站渲染不出来,只能当参考。)


2. 基准拓扑 ​

后面三种能渲染的语法画的都是这一个东西,方便对比表现力:

text
客户端 → Nginx(反向代理) → FastAPI 1 / FastAPI 2 → PostgreSQL
                                                  ↘ Redis

先用最熟悉的 flowchart 打个底:

能用,但表达不了「哪几个组件属于同一层」——只能靠命名暗示,或者上 subgraph:

subgraph 解决了分组,但布局仍然由渲染引擎自动决定,你控制不了方位。


3. architecture-beta:只作语法参考 ​

这是 Mermaid 专门为服务架构设计的语法,概念上确实最像「架构图」:有分组、方位和内置图标。

但在本站渲染不出来,所以本节不提供在线示例

实测在博客的 VitePress 环境(vitepress-plugin-mermaid)中,architecture-beta 代码块浏览器端不出图,页面相应位置是空的。更坑的是:

  • 构建阶段完全静默:npm run build 通过,日志无任何报错
  • 离线用 mermaid.parse() 校验也通过(语法没问题)
  • 甚至用 jsdom 打桩跑 mermaid.render() 都能产出 SVG

只有真实浏览器渲染这一步会失败,且不报错。 所以它没法在本站用来做图示。

想用这套语法的话,建议去 Mermaid Live Editor 或本地 Markdown 预览器里先验证效果,再决定要不要引入。下面只保留语法备忘与踩坑记录。

3.1 语法速查 ​

元素写法说明
分组group <id>(<icon>)["标题"]画成一个大框,服务挂在里面
服务service <id>(<icon>)["标题"]一个节点
归属分组service ... in <group-id>写在服务定义末尾
分叉点junction <id>让一条线分成多条
无向边a:L -- R:b
单向边a:L --> R:b箭头指向 b
反向边a:L <-- R:b箭头指向 a
双向边a:L <--> R:b两端都是箭头
方位L / R / T / B左 / 右 / 上 / 下,贴在节点 id 后面

方位是它设计上最有价值的地方:api1:B -- T:db 表达「FastAPI 1 的下方连到数据库的上方」,渲染时按这个相对位置排。可惜本站用不上。

3.2 三个解析坑 ​

即使将来换个环境用,这三条也得先知道——它们会让解析直接失败:

坑一:中文标题必须加双引号

architecture-beta 的标题词法只接受 ASCII 字符。直接写中文,解析器会在 [ 处直接报错:

text
architecture-beta
    group g(cloud)[云]          ← ❌ Lexer error: unexpected character: ->[<-

architecture-beta
    group g(cloud)["云"]        ← ✅ 加双引号即可

英文标题不受影响,带空格也 OK(["Edge Layer"] 没问题)。但只要有 CJK 字符,必须加引号。

坑二:节点 id 只能是 ASCII

text
service 服务(server)[Server]     ← ❌ 同上,id 处就报错
service svc(server)["服务"]      ← ✅ id 用英文,中文放标题

坑三:内置图标只有 6 个

(cloud)、(server) 这类括号里的是内置图标名。实测可用的只有:

图标适用
cloud分组框、云
server应用服务、Web
database数据库
disk存储、缓存
internet客户端、外部网络
blank占位(不画图标)

写别的名字不会报错,但图标位置会是空的。想要更多图标,得用 mermaid.registerIconPacks() 自己注册图标包。


4. C4:语义最强,适合正式架构文档 ​

C4 模型把架构拆成「人 / 系统 / 容器 / 组件」四层,Mermaid 支持上下文图和容器图。它的价值在于节点类型本身携带语义——一眼能看出哪个是人、哪个是数据库。

常用元素:

元素含义
Person(id, "名称", "描述")使用者/角色
System(id, "名称", "描述")外部系统(上下文图用)
Container(id, "名称", "技术", "描述")应用容器
ContainerDb(id, ...)数据存储
Rel(从, 到, "关系", "技术")带方向的关系
Boundary(...)画一个边界框

中文完全不用引号,这点比 architecture-beta 友好。缺点是布局完全自动,节点多了容易乱;而且节点样式由 C4 主题决定,可定制性低。


5. block-beta:块状栅格布局 ​

block-beta 把图画成显式栅格,用 columns N 指定列数,元素:N 表示跨 N 列。适合画分层拓扑、能力矩阵这种规整的东西。

也可以嵌套 block 做分组:

它的优势是布局完全可预测(你说了算,不是引擎说了算),适合做「系统框图」;代价是连线能力弱,复杂依赖关系表达不了。


6. 同一拓扑,四种画法对比 ​

画法分组方位可控内置图标中文标题连线能力本站可渲染
flowchart需 subgraph❌❌✅强✅
flowchart + subgraph✅❌❌✅强✅
architecture-beta✅✅✅ 6 个⚠️ 要引号中❌
C4Container✅ Boundary❌图标随类型自动✅中✅
block-beta✅ block✅ 栅格❌✅弱✅

7. 选型建议 ​

  • 给非技术同事讲系统长什么样 → C4Container,节点类型自带语义,一眼能分清人和数据库。
  • 正式架构文档 / 需要说明「谁调用谁」 → C4Context + C4Container,分层语义是它的核心价值。
  • 画流程、状态、时序 → 老老实实用 flowchart / stateDiagram / sequenceDiagram,别硬套架构图语法。
  • 需要严格对齐的系统框图 → block-beta。
  • 快速表达依赖关系 → flowchart,成本最低。
  • architecture-beta → 概念上最合适,但本站渲染不出来(第 3 节),只能去 Mermaid Live Editor 用。

8. 坑点汇总 ​

现象原因解决
Lexer error: unexpected character: ->[<-architecture-beta 标题只接受 ASCII中文标题加双引号 ["中文"]
同上,但报错位置在 id 处节点 id 也要求 ASCIIid 用英文,中文写进标题
architecture-beta 图标位置空白用了 6 个内置图标之外的名字换 cloud/server/database/disk/internet/blank,或注册自定义图标包
architecture-beta 页面空白,构建和校验却全绿浏览器端渲染失败但不抛错、不提示;npm run build 静默通过,mermaid.parse() 也通过,jsdom 打桩甚至能产出 SVG交付前在真实浏览器里过一眼;architecture-beta 在本站直接用不了
想验证语法但 Node 里报 DOMPurify.addHook is not a functionNode 无 DOM,dompurify 导出的是工厂函数给 dompurify 打桩(补 sanitize/addHook 空实现)+ 设 securityLevel: 'loose'

两条经验

  1. 离线校验只能证明「语法对」,证明不了「能渲染」。 parse() 过 ≠ 浏览器出图,architecture-beta 就是反例。渲染类问题最终得在浏览器里确认。
  2. 仓库里已经装了 mermaid,可以写脚本把所有 ```mermaid 代码块抽出来逐块 await mermaid.parse(src),至少把语法错误挡在提交之前。

9. 什么时候不该用 Mermaid ​

Mermaid 的定位是「说明型」图示:可 diff、可维护、跟随主题换色。但它有个硬边界——美术可控度低。布局由引擎决定,你改不了节点的精确坐标、圆角、渐变、投影。

如果你的图属于「展示型」:要做封面图、要打印、要拿到站外复用、要精确控制视觉,那就该用手写 SVG:

WSGI 同步阻塞与 ASGI 事件循环对比架构图

上面这张就是手写的 SVG(源码在 docs/notes/tools/images/wsgi-vs-asgi.svg,157 行)。它和 Mermaid 的分工是:

Mermaid手写 SVG
可 diff✅ 纯文本🟡 XML,diff 一般
跟随深浅色主题✅ 自动❌ 配色写死
改动成本改一行调坐标
美术可控度低高
打印 / 站外复用❌ 依赖 JS✅ 哪都能打开

结论:文章内的说明性图示用 Mermaid,撑门面的架构总图用手写 SVG。


10. 小结 ​

要点说明
architecture-beta 本站用不了语法本身不错(有分组、方位、内置图标),但浏览器端渲染失败且不报错,只能去 Mermaid Live Editor 用;语法备忘与解析坑见第 3 节
C4 语义最强节点类型自带含义,适合正式架构文档,中文无需引号
block-beta 布局可控栅格由你说了算,适合系统框图,连线能力弱
flowchart 依然是默认选择成本最低、能力最全,只是分组和方位要妥协
语法对 ≠ 能渲染mermaid.parse() 通过不代表浏览器出图,渲染问题最终得在真实浏览器确认
构建不会帮你发现 Mermaid 错误构建期不解析 Mermaid,写错也不报,离线 parse() 至少能挡住语法错误
展示型图别硬用 Mermaid美术可控度是硬边界,该上 SVG 就上 SVG
📖本文阅读--次|📊全站访问--次|👥访客--人