mysqldump 默认导出结构和数据,只导表结构必须显式添加 --no-data 参数;该参数为开关型,须置于数据库名前,且必须指定数据库名,否则报错。

mysqldump 加 --no-data 才能只导出表结构
直接跑 mysqldump 默认会导出结构+数据,想只留结构必须显式加 --no-data。漏掉这个参数,备份文件里全是 INSERT 语句,完全不是你想要的。
常见错误现象:mysqldump mydb users > users.sql 导出来的文件打开一看,几百行 INSERT INTO users VALUES (...),根本没注意它默认带数据。
-
--no-data是开关型参数,不接受值,写成--no-data=1或--no-data true会报错 - 必须跟在
mysqldump命令后、数据库名之前,顺序错(比如放最后)可能被忽略 - 如果同时用
--skip-triggers或--routines,它们和--no-data互不冲突,但要注意触发器/存储过程本身也属于“结构”,默认不导出,需额外加参数
导出单表结构时别漏掉数据库名
mysqldump --no-data 不像某些工具能自动推断上下文,它强制要求指定数据库名。只写 mysqldump --no-data users 会报错:mysqldump: Couldn't find table: 'users' —— 它以为 users 是数据库名,不是表名。
正确写法是:mysqldump --no-data mydb users > users_schema.sql。这里 mydb 是数据库名,users 是表名,缺一不可。
- 导多张表就挨个列出来:
mysqldump --no-data mydb users posts comments > schema.sql - 想导整个库的结构(不含数据),直接省略表名:
mysqldump --no-data mydb > mydb_schema.sql - 如果表名含特殊字符或关键字,用反引号包住:
mysqldump --no-data mydb `order`
注意 CREATE TABLE 语句里的引擎和字符集是否符合预期
mysqldump --no-data 输出的 CREATE TABLE 语句,会如实反映原表当前的 ENGINE、CHARSET、COLLATE 等属性。但如果你导出后准备在另一套环境重建,这些细节可能引发兼容性问题。
例如:原表用 InnoDB,目标 MySQL 版本不支持该引擎(极少见),或字符集是 utf8mb4_0900_ai_ci,而旧版本 MySQL 不识别这个排序规则,CREATE TABLE 就会失败。
- 加
--compatible=mysql40可降级语法(如去掉ROW_FORMAT),但会丢失部分元信息 - 用
--default-character-set=utf8mb4显式指定字符集,避免依赖客户端默认值 - 导出后快速扫一眼开头几行,确认
ENGINE=和DEFAULT CHARSET=是你期望的
权限不足时 mysqldump 会静默跳过某些结构
如果执行 mysqldump --no-data 的账号没有 SELECT 权限(哪怕只是查 information_schema),它不会报错,但可能漏掉外键定义、分区信息,甚至整张表都不出现——尤其是视图、存储过程这类依赖额外权限的对象。
典型表现:导出文件里有 CREATE TABLE t1,但没有 CREATE TABLE t2,而你知道 t2 存在;或者外键约束全没了,CREATE TABLE 末尾干干净净没 FOREIGN KEY。
- 最低权限要求:
SELECT+SHOW VIEW(对视图)+LOCK TABLES(即使--no-data也会尝试锁表,可加--skip-lock-tables规避) - 检查权限用:
SHOW GRANTS FOR CURRENT_USER; - 如果只是临时导结构,用
root或高权限账号最省事,别卡在权限排查上
--no-data 后面跟着的权限、字符集、表名位置、引擎兼容性,哪一环松动都可能让重建失败。最稳妥的做法是:导完立刻用 head -20 看前20行,确认是干净的 CREATE TABLE,再检查最后一张表有没有被截断。











