如何复制表的结构、约束与触发器至另一表?现有命令仅复制结构数据
复制表结构、数据、约束及触发器的解决方案
CREATE TABLE demo AS TABLE niu_trans_stats WITH DATA 仅能复制表的基础结构和数据,主键、外键、唯一约束、检查约束以及触发器这类对象不会被自动复制,需要手动处理,具体步骤如下:
一、复制约束
1. 提取并创建主键约束
不同数据库的系统查询表不同,以下以PostgreSQL和DB2为例:
- PostgreSQL:
SELECT a.attname FROM pg_index i JOIN pg_attribute a ON a.attrelid = i.indrelid AND a.attnum = ANY(i.indkey) WHERE i.indrelid = 'niu_trans_stats'::regclass AND i.indisprimary;
得到主键字段后,在新表上执行:
ALTER TABLE demo ADD PRIMARY KEY (字段1, 字段2); -- 替换为实际主键字段
- DB2:
SELECT COLNAME FROM SYSCAT.COLUMNS WHERE TABNAME = 'NIU_TRANS_STATS' AND IDENTITY = 'Y' OR (TABNAME = 'NIU_TRANS_STATS' AND COLNAME IN ( SELECT COLNAME FROM SYSCAT.KEYCOLUSE WHERE TABNAME = 'NIU_TRANS_STATS' AND CONSTRAINTTYPE = 'P' ));
创建主键:
ALTER TABLE demo ADD PRIMARY KEY (字段1, 字段2);
2. 提取并创建唯一约束
- PostgreSQL:
SELECT conname, array_agg(attname) AS cols FROM pg_constraint c JOIN pg_attribute a ON a.attrelid = c.conrelid AND a.attnum = ANY(c.conkey) WHERE c.conrelid = 'niu_trans_stats'::regclass AND c.contype = 'u' GROUP BY conname;
生成创建语句并执行:
ALTER TABLE demo ADD CONSTRAINT demo_唯一约束名 UNIQUE (字段1, 字段2); -- 替换约束名和字段
- DB2:
SELECT CONSTRAINTNAME, COLNAME FROM SYSCAT.KEYCOLUSE WHERE TABNAME = 'NIU_TRANS_STATS' AND CONSTRAINTTYPE = 'U';
创建唯一约束:
ALTER TABLE demo ADD CONSTRAINT demo_唯一约束名 UNIQUE (字段1, 字段2);
3. 外键与检查约束
用类似方式查询系统表获取原表的外键、检查约束定义,替换表名为demo后执行对应的ALTER TABLE语句即可。比如PostgreSQL中查询检查约束:
SELECT conname, consrc FROM pg_constraint WHERE conrelid = 'niu_trans_stats'::regclass AND contype = 'c';
创建检查约束:
ALTER TABLE demo ADD CONSTRAINT demo_检查约束名 CHECK (约束条件);
二、复制触发器
PostgreSQL:
查询原表的触发器定义(排除系统内置触发器):
SELECT pg_get_triggerdef(t.oid) AS trigger_def FROM pg_trigger t JOIN pg_class c ON t.tgrelid = c.oid WHERE c.relname = 'niu_trans_stats' AND NOT t.tgisinternal;
将查询结果中的原表名niu_trans_stats替换为demo,直接执行这些语句即可创建触发器。
DB2:
查询触发器定义:
SELECT TEXT FROM SYSCAT.TRIGGERS WHERE TABNAME = 'NIU_TRANS_STATS' AND OWNER = '你的用户名'; -- 替换为实际用户名
同样替换表名后执行语句创建触发器。
额外注意事项
如果原表主键使用了序列(比如PostgreSQL的SERIAL/BIGSERIAL),CREATE TABLE ... AS不会自动关联序列,需要手动设置默认值:
ALTER TABLE demo ALTER COLUMN 主键字段 SET DEFAULT nextval('原表序列名');
内容的提问来源于stack exchange,提问作者sandesh Jadhav
相关产品推荐
相关产品推荐

