drawDB v1.8.2 快速入门(绘制 ER 图到导出 SQL)

drawDB v1.8.2 快速入门:从打开编辑器到完成第一张 ER 图的全流程实操——认识工作区、新建表格、建立关系、使用模板、导出六种方言 SQL、DBML/Mermaid 导出与 SQL 反向解析,全部步骤经源码级实测验证。

drawDBdrawDBER 图SQL2026/10/17

drawDB v1.8.2 快速入门(绘制 ER 图到导出 SQL)

目标:部署好 drawDB v1.8.2 后(安装见《drawDB v1.8.2 Ubuntu 22.04 安装指南》,Compose 部署见《drawDB v1.8.2 Docker Compose 部署指南》),从打开编辑器到导出第一份可执行 SQL 的完整上手流程。文中全部界面文案、导出 SQL、DBML/Mermaid 输出均取自 v1.8.2 源码级实测,可对照复现。已在 Ubuntu 22.04.5 LTS(x86_64)环境实测通过。

一、环境信息

  • 操作系统:Ubuntu 22.04.5 LTS(x86_64)
  • drawDB 版本:v1.8.2,Docker Compose 镜像部署(安装与部署过程见《drawDB v1.8.2 Ubuntu 22.04 安装指南》《drawDB v1.8.2 Docker Compose 部署指南》)
  • 端口与访问地址:Compose 映射端口 3000,编辑器访问 http://192.168.1.231:3000/(示例地址,换成实际部署地址)
  • 图表数据存储:浏览器本地 IndexedDB,服务端不存任何图表数据
  • 分享功能依赖:drawdb-server 分享后端,地址经 VITE_BACKEND_URL 环境变量注入,未配置不影响绘图与导出

二、界面与核心概念

2.1 打开编辑器

浏览器访问部署地址(本文以 http://192.168.1.231:3000/ 为例,换成你的实际地址),首页点击「Open Editor」按钮,进入编辑器工作区。也可直接访问 http://192.168.1.231:3000/editor。

2.2 工作区布局

编辑器由四部分组成:

区域位置作用
顶部工具栏页面上方新建表格/关系/区域/备注、撤销重做、撤销缩放、主题、设置、导出
左侧对象列表左边栏当前图中的表、关系、区域、备注清单,点击定位画布
中央画布中部拖放式绘图区,表格卡片、关系连线都在这里操作
右侧属性面板右边栏(选中对象时出现)编辑选中表格/关系的字段、约束、颜色等属性

底部还有一个「To-do list」侧栏(待办清单),与绘图无关,可忽略。

💡 技术拓展:首次进入会弹出欢迎引导(含 3 步滑动说明与「Start」按钮),引导文案同样可在「Settings → Language」切换界面语言后再看。drawDB 内置多语言(简体中文等),但生成 SQL 的注释文字取决于你在表格/字段上填写的 comment 内容,与界面语言无关。

2.3 核心概念速览

概念说明对应 SQL 产物
Table(表)实体,含字段/索引/唯一约束CREATE TABLE
Field(字段)列,可设主键/自增/非空/唯一/默认值/check列定义
Relationship(关系)表间外键连线,含基数与更新/删除约束ALTER TABLE ADD FOREIGN KEY
Index(索引)表上的普通/唯一索引CREATE INDEX
Area(区域)画布上的分组色块,仅视觉效果不生成 SQL
Note(备注)画布上的便签不生成 SQL(部分方言转注释)
Type/Enum/View自定义类型/枚举/视图(PostgreSQL 等方言支持)对应 DDL

三、第一张 ER 图:用户-订单模型

本章从零绘制经典的「users—orders」一对多模型,全程在 http://192.168.1.231:3000/editor 实操。

3.1 新建两张表

点击顶部工具栏「Add table」按钮(或快捷键 Ctrl+Alt+T),画布出现一张新表卡片,默认名 table_name。点击表格标题(或从左侧列表点击该表),右侧属性面板进入编辑态:

  1. 表名改为 users;
  2. 注释(comment)填 用户表;
  3. 点色块选一个表头颜色(默认蓝色 #7d9dff)。

默认字段结构(新建表自带 3 个空字段):

属性默认值
字段名field_name
类型INTEGER
主键/唯一/非空/自增均未勾选
大小(size)空
默认值/检查空

把 users 表的字段按下表设置(在右侧面板逐行编辑):

字段名类型属性说明
idINT主键 + 自增 + 非空,unsigned 勾选主键
usernameVARCHAR,size 64非空 + 唯一用户名
emailVARCHAR,size 128非空 + 唯一邮箱
created_atTIMESTAMP非空,默认值 CURRENT_TIMESTAMP创建时间

再次「Add table」创建第二张表 orders(注释 订单表,颜色可换绿色 #89e667),字段:

字段名类型属性
idINT主键 + 自增 + 非空,unsigned 勾选
user_idINT非空,unsigned 勾选
amountDECIMAL,size 10,2非空

拖动表格标题栏把两张表在画布上摆开(左右并排),画布支持滚轮缩放、按住空白处平移。

3.2 建立关系(外键连线)

点击工具栏「Add relationship」(快捷键 Ctrl+Alt+R)后进入连线模式,先点子表 orders 的 user_id 字段,再点父表 users 的 id 字段,画布上出现连线。选中连线后在右侧面板设置:

属性取值说明
Cardinality(基数)Many to oneorders 多行对 users 一行
Update constraintNo action父表主键更新时不级联
Delete constraintCascade父表记录删除时级联删除子记录

💡 技术拓展:基数(Cardinality)与约束动作是 ER 建模的两个易混维度。drawDB 支持的基数三种:One to one(1:1)、One to many(1:N)、Many to one(N:1)——绘制方向不同只是连线形态不同,最终都落到「子表字段引用父表主键」的外键。约束动作五种(对应关系下拉项):No action / Restrict / Cascade / Set null / Set default,其语义由目标数据库引擎执行,drawDB 只负责翻译成 DDL(如 ON DELETE CASCADE)。

常见库对外键约束的支持差异:SQLite 语法上接受外键但默认关闭强制执行(需 PRAGMA foreign_keys = ON);MySQL InnoDB 支持 No action/Restrict/Cascade/Set null 但不支持 Set default;PostgreSQL 全部支持。设计跨库模型时约束动作建议保守用 Cascade 或 No action。

3.3 自动连线(可选)

多表场景可让 drawDB 自动识别外键:工具栏「Auto-connect foreign keys」,其识别规则(官方界面原文):

  • Rule 1 — Table Prefix + PK Column(表前缀 + 主键列,如 user_id 或 users_id 关联到主键为 id 的 users 表);
  • Rule 2 — Matching PK Column Name(同名主键列匹配,如子表 author_id 匹配父表同名 author_id 列)。

实测确认自动生成的连线命名为 fk_<子表>_<外键字段>_<父表> 形态(如 fk_orders_user_id_users),与手工连线行为一致。

3.4 画布辅助操作

操作入口/快捷键
缩放到合适视图工具栏「Fit window」或 Ctrl+Alt+0(Fit window / Reset)
一键整理布局工具栏「Auto arrange」
网格显示/吸附设置面板 Show grid / Snap to grid
添加区域/备注「Add area」Ctrl+Alt+A /「Add note」Ctrl+Alt+N
撤销/重做Ctrl+Z / Ctrl+Y

四、保存与图表数据

4.1 自动保存到哪里

编辑器默认开启自动保存(设置项 Autosave 默认 On),图表数据保存在浏览器本地 IndexedDB,服务器不存任何图表数据。关掉标签页再打开,图表仍在。

⚠️ 注意:清理浏览器数据、换浏览器/设备都会导致图表"消失"。重要图表务必导出 JSON 文件备份(见 4.2)。多设备同步可用「Export saved data」导出再在另一设备导入。

4.2 图表 JSON 导出/导入

  • 导出:工具栏「Export as」→「JSON」,得到 .json 文件(结构含 tables、relationships、notes、subjectAreas、views、database 等字段,实测 v1.8.2 导出字段即此清单);
  • 导入:工作台「Import diagram」→ 选择 JSON 文件(或直接把 JSON 文件拖入页面)。

JSON 是 drawDB 的完整工程格式,可版本库管理、二次编辑、跨环境迁移。

4.3 存为内置模板与 Fork

  • 工具栏「Save as template」把当前图存成个人模板,之后在「Templates」页可一键复用;
  • 浏览官方内置模板:首页或编辑器左侧「Templates」进入,v1.8.2 内置 6 套:Blog database schema、Human resources schema、E-commerce schema、Library schema、Bank schema、University schema。模板页点「Use this template」即复制到编辑器。

五、导出 SQL

5.1 选择目标数据库方言

编辑器右上角(设置面板或工具栏数据库下拉)选择目标方言,可选项:MySQL、PostgreSQL、MariaDB、SQL Server(界面显示 TransactSQL)、SQLite、Oracle SQL。切换方言只影响后续导出的 SQL 语法,不影响画布图形。

5.2 导出操作

工具栏「Export SQL」→ 选「SQL」(或「Export as」→「SQL」),浏览器下载 .sql 文件(文件名默认取图表名,如 test.sql)。

5.3 实测导出结果对照(同一张 users-orders 图)

以下为 3.1/3.2 绘制的同一模型在六种方言下的真实导出内容(v1.8.2 实测逐字原文,可逐行对照验证)。

MySQL:

CREATE TABLE IF NOT EXISTS `users` (
	`id` INT NOT NULL AUTO_INCREMENT COMMENT '主键',
	`username` VARCHAR(64) NOT NULL UNIQUE COMMENT '用户名',
	`email` VARCHAR(128) NOT NULL UNIQUE,
	`created_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
	PRIMARY KEY(`id`)
) COMMENT='用户表';


CREATE TABLE IF NOT EXISTS `orders` (
	`id` INT NOT NULL AUTO_INCREMENT,
	`user_id` INT NOT NULL,
	`amount` DECIMAL(10,2) NOT NULL,
	PRIMARY KEY(`id`)
) COMMENT='订单表';


ALTER TABLE `orders`
ADD FOREIGN KEY(`user_id`) REFERENCES `users`(`id`)
ON UPDATE NO ACTION ON DELETE CASCADE;

PostgreSQL:

CREATE TABLE IF NOT EXISTS "users" (
	-- 主键
	"id" INT NOT NULL GENERATED BY DEFAULT AS IDENTITY,
	-- 用户名
	"username" VARCHAR(64) NOT NULL UNIQUE,
	"email" VARCHAR(128) NOT NULL UNIQUE,
	"created_at" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
	PRIMARY KEY("id")
);

COMMENT ON TABLE "users" IS '用户表';
COMMENT ON COLUMN "users"."id" IS '主键';
COMMENT ON COLUMN "users"."username" IS '用户名';

CREATE TABLE IF NOT EXISTS "orders" (
	"id" INT NOT NULL GENERATED BY DEFAULT AS IDENTITY,
	"user_id" INT NOT NULL,
	"amount" DECIMAL(10,2) NOT NULL,
	PRIMARY KEY("id")
);

COMMENT ON TABLE "orders" IS '订单表';

ALTER TABLE "orders"
ADD FOREIGN KEY("user_id") REFERENCES "users"("id")
ON UPDATE NO ACTION ON DELETE CASCADE;

MariaDB:

CREATE OR REPLACE TABLE `users` (
	`id` INT UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '主键',
	`username` VARCHAR(64) NOT NULL UNIQUE COMMENT '用户名',
	`email` VARCHAR(128) NOT NULL UNIQUE,
	`created_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
	PRIMARY KEY(`id`)
) COMMENT='用户表';

CREATE OR REPLACE TABLE `orders` (
	`id` INT UNSIGNED NOT NULL AUTO_INCREMENT,
	`user_id` INT UNSIGNED NOT NULL,
	`amount` DECIMAL(10,2) NOT NULL,
	PRIMARY KEY(`id`)
) COMMENT='订单表';

ALTER TABLE `orders`
ADD FOREIGN KEY(`user_id`) REFERENCES `users`(`id`)
ON UPDATE NO ACTION ON DELETE CASCADE;

SQL Server(TransactSQL):

CREATE TABLE [users] (
	[id] INT NOT NULL IDENTITY,
	[username] VARCHAR(64) NOT NULL UNIQUE,
	[email] VARCHAR(128) NOT NULL UNIQUE,
	[created_at] TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
	PRIMARY KEY([id])
);
GO

EXEC sys.sp_addextendedproperty
    @name=N'MS_Description', @value=N'用户表',
    @level0type=N'SCHEMA',@level0name=N'dbo',
    @level1type=N'TABLE',@level1name=N'users';
GO

CREATE TABLE [orders] (
	[id] INT NOT NULL IDENTITY,
	[user_id] INT NOT NULL,
	[amount] DECIMAL(10,2) NOT NULL,
	PRIMARY KEY([id])
);
GO

ALTER TABLE [orders]
ADD FOREIGN KEY([user_id])
REFERENCES [users]([id])
ON UPDATE NO ACTION ON DELETE CASCADE;
GO

(完整输出中每张表、每个带注释字段都有独立的 sp_addextendedproperty 语句,此处为排版节选,逻辑不变。)

SQLite:

/* 用户表 */
CREATE TABLE IF NOT EXISTS "users" (
	-- 主键
	"id" INT NOT NULL,
	-- 用户名
	"username" VARCHAR NOT NULL UNIQUE,
	"email" VARCHAR NOT NULL UNIQUE,
	"created_at" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
	PRIMARY KEY("id")
);

/* 订单表 */
CREATE TABLE IF NOT EXISTS "orders" (
	"id" INT NOT NULL,
	"user_id" INT NOT NULL,
	"amount" DECIMAL NOT NULL,
	PRIMARY KEY("id"),
	FOREIGN KEY ("user_id") REFERENCES "users"("id")
	ON UPDATE NO ACTION ON DELETE CASCADE
);

Oracle SQL:

/* 用户表 */
CREATE TABLE "users" (
	-- 主键
	"id" INT NOT NULL GENERATED ALWAYS AS IDENTITY,
	-- 用户名
	"username" VARCHAR(64) NOT NULL UNIQUE,
	"email" VARCHAR(128) NOT NULL UNIQUE,
	"created_at" TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
	PRIMARY KEY("id")
);


/* 订单表 */
CREATE TABLE "orders" (
	"id" INT NOT NULL GENERATED ALWAYS AS IDENTITY,
	"user_id" INT NOT NULL,
	"amount" DECIMAL(10,2) NOT NULL,
	PRIMARY KEY("id")
);


ALTER TABLE "orders"
ADD CONSTRAINT "fk_orders_user_id_users" FOREIGN KEY ("user_id") REFERENCES "users" ("id")
ON DELETE CASCADE;

5.4 方言差异要点(实测归纳)

差异点MySQLPostgreSQLMariaDBSQL ServerSQLiteOracle
建表防重复IF NOT EXISTSIF NOT EXISTSCREATE OR REPLACE无(需手写判断)IF NOT EXISTS无
自增主键AUTO_INCREMENTGENERATED BY DEFAULT AS IDENTITYAUTO_INCREMENTIDENTITYAUTOINCREMENT 需显式列属性GENERATED ALWAYS AS IDENTITY
注释落地行内 COMMENT/表尾 COMMENT=COMMENT ON 独立语句行内 COMMENTsp_addextendedproperty 存储过程/* */ 与 -- 注释/* */ 与 -- 注释
UNSIGNED 类型支持不支持(忽略)支持不支持(忽略)不支持(忽略)不支持(忽略)
标识符引号反引号 `双引号 "反引号 `方括号 []双引号 "双引号 "
外键写法独立 ALTER TABLE独立 ALTER TABLE独立 ALTER TABLEALTER TABLE + GO表内 FOREIGN KEY 子句ALTER TABLE + 显式约束名

💡 技术拓展:MySQL 导出中 UNSIGNED 被 drop(drawDB v1.8.2 的 MySQL 导出器忽略 unsigned 属性,INT UNSIGNED 输出为 INT),而 MariaDB 导出器保留 INT UNSIGNED——两个库导出器不同源所致。若模型强依赖 MySQL 无符号整数语义,选择 MariaDB 方言导出或导出后手工补。另外 Oracle 导出会给外键加显式约束名(如 fk_orders_user_id_users),其余方言用匿名外键。

六、导出其他格式

「Export as」菜单(实测完整清单):

格式用途说明
SQL当前方言 DDL见第五章
PNG / JPEG图表图片PNG 可调清晰度;JPEG 质量固定 0.95
SVG矢量图可无限放大,文档嵌入首选
JSONdrawDB 工程文件完整备份/迁移(见 4.2)
DBMLdbdiagram.io 生态格式文本化建模语言
PDF文档交付横向版式(landscape)
MermaidMarkdown 内嵌 ER 图.md 文件,GitHub/GitLab 原生渲染
Markdown结构化文档逐表列出字段属性的文档

6.1 DBML 实测输出

Table users [headercolor: #7d9dff] {
	id int [ pk, increment, not null, note: '主键' ]
	username varchar(64) [ not null, unique, note: '用户名' ]
	email varchar(128) [ not null, unique ]

	Note: '用户表'
}

Table orders [headercolor: #89e667] {
	id int [ pk, increment, not null ]
	user_id int [ not null ]
	amount decimal(10,2) [ not null ]

	Note: '订单表'
}

Ref fk_orders_user_id_users {
	orders.user_id > users.id [ delete: cascade, update: no action ]
}

DBML 可直接粘贴到 dbdiagram.io/dbdocs.io 渲染,或存入仓库做"配置即文档"。

6.2 Mermaid 实测输出

erDiagram
	orders }o--|| users : references

	users {
		INT id
		VARCHAR(64) username
		VARCHAR(128) email
	}

	orders {
		INT id
		INT user_id
		DECIMAL(10,2) amount
	}

把这段 erDiagram 代码块放进任意 Markdown(如 README.md),GitHub 会直接渲染成 ER 图。

七、SQL 反向解析(Import from SQL)

把已有数据库的 DDL 导入 drawDB 还原成图,用于"存量库可视化"。

7.1 操作入口

工作台(首页)点「Import from SQL」(编辑器内为「Import diagram → Import from SQL」),粘贴/上传 SQL,选择源方言后确认。

7.2 实测:一段 MySQL DDL 反向解析

输入(建表语句见下):

CREATE TABLE users (
  id INT UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '主键',
  username VARCHAR(64) NOT NULL UNIQUE,
  email VARCHAR(128) NOT NULL,
  created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
  PRIMARY KEY (id)
);
CREATE TABLE orders (
  id INT UNSIGNED NOT NULL AUTO_INCREMENT,
  user_id INT UNSIGNED NOT NULL,
  amount DECIMAL(10,2) NOT NULL,
  PRIMARY KEY (id),
  FOREIGN KEY (user_id) REFERENCES users (id) ON DELETE CASCADE
);

实测解析结果(v1.8.2 逐字原文):

TABLE users fields= id:INTEGER(PK)(AI), username:VARCHAR(UQ), email:VARCHAR, created_at:TIMESTAMP
TABLE orders fields= id:INTEGER(PK)(AI), user_id:INTEGER, amount:DECIMAL
{"start":"orders","end":"users","cardinality":"many_to_one","deleteConstraint":"Cascade"}

即:两张表、users.id 识别为主键+自增、username 保留唯一约束、orders.user_id → users.id 自动还原成 Many to one 关系且删除约束为 Cascade。

7.3 反向解析能力边界(实测结论)

输入特性是否保留实测说明
表/字段/主键/非空/唯一✅完整保留
自增(AUTO_INCREMENT)✅还原为自增字段
外键 + ON DELETE 约束✅还原为关系连线
字段 COMMENT✅还原为字段注释(round-trip 后保留 '主键')
UNSIGNED 属性⚠️ 丢失INT UNSIGNED 经解析后类型变 INTEGER(v1.8.2 实测)
类型名规范化⚠️INT 可能被解析引擎规范为 INTEGER,再导出时以此为准

Round-trip 实测:上面的 SQL 解析成图后立即再导出 MySQL,结果(逐字原文):

CREATE TABLE IF NOT EXISTS `users` (
	`id` INTEGER NOT NULL AUTO_INCREMENT COMMENT '主键',
	`username` VARCHAR(64) NOT NULL UNIQUE,
	`email` VARCHAR(128) NOT NULL,
	`created_at` TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
	PRIMARY KEY(`id`)
);


CREATE TABLE IF NOT EXISTS `orders` (
	`id` INTEGER NOT NULL AUTO_INCREMENT,
	`user_id` INTEGER NOT NULL,
	`amount` DECIMAL(10,2) NOT NULL,
	PRIMARY KEY(`id`)
);


ALTER TABLE `orders`
ADD FOREIGN KEY(`user_id`) REFERENCES `users`(`id`)
ON UPDATE NO ACTION ON DELETE CASCADE;

对比可见:INT → INTEGER、UNIQUE 从 username 行移除(唯一约束转入图内的字段属性,字段上仍标记 UQ)、新导出自动带 IF NOT EXISTS。结论:反向解析适合"看图",round-trip 不是无损克隆,DDL 交付请以原始 SQL 为准。

💡 技术拓展:drawDB 的 SQL 解析基于 node-sql-parser(Oracle 方言用 oracle-sql-parser),因此其能力边界与该解析器一致——复杂存储过程、触发器、非标准方言扩展(如 MySQL 分区子句)不在解析范围。反向解析前先把 DDL 清理到纯 CREATE TABLE/FOREIGN KEY 语句最稳。

八、分享与协作

  • 「Share」入口可把当前图表生成只读链接,前提是实例配置了 drawdb-server 分享后端(VITE_BACKEND_URL,见《drawDB v1.8.2 配置参数详解》);未配置时点击分享会连接失败,属预期行为。
  • 无后端时的协作替代:导出 JSON 文件互相拷贝导入;或将 JSON 提交到代码仓库评审。

九、常见问题(FAQ)

Q1:导出的 SQL 里表注释变成了独立语句/注释行,和行内 COMMENT 不一样? 方言差异的正常行为(见 5.4 表格):MySQL/MariaDB 落在行内 COMMENT,PostgreSQL 用 COMMENT ON,SQL Server 用 sp_addextendedproperty,SQLite/Oracle 用 SQL 注释。语义等价,执行后注释均可查。

Q2:勾了 unsigned 但 MySQL 导出里没有? v1.8.2 MySQL 导出器忽略 unsigned(MariaDB 导出器保留)。需要无符号语义时用 MariaDB 方言导出。

Q3:字段下拉里找不到我要的类型? 类型清单随方言变化(如 enum 仅部分方言)。先用相近类型绘制,导出后手工替换;或直接在字段类型框输入自定义类型名。

Q4:图标表太大导出 PNG 被截断? 先「Fit window / Reset」把整图纳入视口再导出;导出前在设置里调高图像清晰度(pixelRatio)可获得更大分辨率。

Q5:换了浏览器/电脑图表不见了? 图表存在浏览器本地(IndexedDB)。在原浏览器导出 JSON,再到新环境导入即可。

Q6:自动连线把不相关表连起来了? Auto-connect 按命名规则匹配(表前缀+主键 / 同名列),撞名会误连。删除误连的关系线后手工建立正确连线即可,主键命名规范(<表>_id)能显著降低误连率。

十、下一步

十一、参考链接