能批量导出SQL触发器定义脚本,但需分数据库类型处理:MySQL用SHOW CREATE TRIGGER逐个查(因INFORMATION_SCHEMA.TRIGGERS的ACTION_STATEMENT被截断);PostgreSQL用pg_get_triggerdef()关联pg_trigger和pg_class过滤普通表;SQL Server用sys.triggers结合OBJECT_DEFINITION(),并处理加密触发器和库名前缀。

能批量导出 SQL 触发器定义脚本,但必须分数据库类型处理——MySQL、PostgreSQL 和 SQL Server 的机制完全不同,硬套一个脚本会失败。
MySQL:用 SHOW CREATE TRIGGER 逐个查,别信 INFORMATION_SCHEMA.TRIGGERS 的 ACTION_STATEMENT
MySQL 的 INFORMATION_SCHEMA.TRIGGERS 表里 ACTION_STATEMENT 字段是被截断的(默认只存前 64KB),根本不能直接当完整定义用。真正可靠的是 SHOW CREATE TRIGGER,但它不支持批量执行,得写循环。
- 先查出所有触发器名:
SELECT CONCAT('SHOW CREATE TRIGGER `', TRIGGER_NAME, '`;') FROM INFORMATION_SCHEMA.TRIGGERS WHERE EVENT_SCHEMA = 'your_db'; - 把结果复制进客户端执行,或用 shell +
mysql -e拼接生成临时 SQL 文件 - 注意:触发器名带特殊字符时,
CONCAT生成的语句必须用反引号包裹,否则报错ERROR 1064 - 导出结果里包含
DELIMITER和CREATE DEFINER,若要跨环境部署,得用sed或 Python 替换掉DEFINER=`user`@`host`
PostgreSQL:用 pg_get_triggerdef() + pg_trigger 关联,别漏掉 pg_class
PostgreSQL 没有“一键导出所有触发器”的元命令,\dt+ 只看表,\df+ 只看函数。触发器定义藏在系统目录里,必须手动 JOIN。
- 核心组合是:
SELECT pg_get_triggerdef(oid) FROM pg_trigger WHERE tgrelid IN (SELECT oid FROM pg_class WHERE relkind = 'r'); -
tgrelid是触发器绑定的表 OID,必须通过pg_class过滤出普通表(relkind = 'r'),否则会混入视图、分区子表等无效对象 -
pg_get_triggerdef()返回的字符串默认不含CREATE TRIGGER开头,需要自己拼:'CREATE TRIGGER ' || tgname || ' ' || pg_get_triggerdef(oid) - 如果触发器依赖自定义函数,
pg_get_triggerdef()不自动导出函数体,得额外跑一遍pg_get_functiondef()
SQL Server:用 sys.triggers + OBJECT_DEFINITION(),警惕加密触发器
SQL Server 的 sys.triggers 能列出所有触发器,OBJECT_DEFINITION() 可取定义,但加密触发器会返回 NULL,且没有提示。
- 基础查询:
SELECT name, OBJECT_DEFINITION(object_id) FROM sys.triggers WHERE parent_class = 1;(parent_class = 1表示绑定到表) - 必须加
WHERE is_ms_shipped = 0过滤掉系统自带触发器,否则导出会混入queue_messages_XXXXX这类内部对象 - 遇到
OBJECT_DEFINITION()返回NULL,先查sys.sql_modules的is_encrypted字段确认是否加密;加密的只能靠 SSMS 右键“脚本为 → 创建”,没法自动化 - 导出结果里的
CREATE TRIGGER语句默认含数据库名前缀(如[MyDB].[dbo].[MyTrigger]),跨库迁移时得用正则删掉库名部分
真正麻烦的不是语法,而是每个数据库对“触发器所属对象”的判定逻辑不同:MySQL 绑定到表+模式,PostgreSQL 绑定到表但可能跨 schema,SQL Server 还分 AFTER/INSTEAD OF 且能绑定到视图。导出脚本前,先确认目标环境是否支持你导出的触发器类型,不然白忙活。

















