sql – 表中的多个约束:如何获取所有违规?
我在Oracle中有一个表,有几个限制.当我插入一个新的记录,并不是所有的约束是有效的,那么Oracle只会引发“第一个”错误.如何获得所有违反我记录的行为?
CREATE TABLE A_TABLE_TEST ( COL_1 NUMBER NOT NULL,COL_2 NUMBER NOT NULL,COL_3 NUMBER NOT NULL,COL_4 NUMBER NOT NULL ); INSERT INTO A_TABLE_TEST values (1,null,2); ORA-01400: cannot insert NULL into ("USER_4_8483C"."A_TABLE_TEST"."COL_2") 我想得到这样的东西: Column COL_2: cannot insert NULL Column COL_3: cannot insert NULL This would be also sufficient: Column COL_2: not valid Column COL_3: not valid 当然我可以写一个触发器并单独检查每个列,但我喜欢限制而不是触发器,它们更容易维护,不需要手动编写代码. 任何想法? 解决方法没有直接的方式报告所有可能的约束违规.因为当Oracle在第一次违反约束时绊倒时,不能再进行评估,否则语句失败,除非该约束被延迟,否则日志错误子句已被包含在DML语句中.但是应该注意的是,log errors子句将无法捕获所有可能的约束违例,只记录第一个.作为可能的方法之一是: >创建异常表.可以通过执行ora_home / rdbms / admin / utlexpt.sql脚本来完成.桌子的结构很简单; 测试表: create table t1( col1 number not null,col2 number not null,col3 number not null,col4 number not null ); 尝试执行一个insert语句: insert into t1(col1,col2,col3,col4) values(1,2,null); Error report - SQL Error: ORA-01400: cannot insert NULL into ("HR"."T1"."COL2") 禁用所有表的约束: alter table T1 disable constraint SYS_C009951; alter table T1 disable constraint SYS_C009950; alter table T1 disable constraint SYS_C009953; alter table T1 disable constraint SYS_C009952; 尝试再次执行以前失败的insert语句: insert into t1(col1,null); 1 rows inserted. commit; 现在,在异常表中启用表的约束并存储异常(如果有): alter table T1 enable constraint SYS_C009951 exceptions into exceptions; alter table T1 enable constraint SYS_C009950 exceptions into exceptions; alter table T1 enable constraint SYS_C009953 exceptions into exceptions; alter table T1 enable constraint SYS_C009952 exceptions into exceptions; 检查例外表: column row_id format a30; column owner format a7; column table_name format a10; column constraint format a12; select * from exceptions ROW_ID OWNER TABLE_NAME CONSTRAINT ------------------------------ ------- ------- ------------ AAAWmUAAJAAAF6WAAA HR T1 SYS_C009951 AAAWmUAAJAAAF6WAAA HR T1 SYS_C009953 两个限制已被违反.要查找列名,只需参考user_cons_columns数据字典视图: column table_name format a10; column column_name format a7; column row_id format a20; select e.table_name,t.COLUMN_NAME,e.ROW_ID from user_cons_columns t join exceptions e on (e.constraint = t.constraint_name) TABLE_NAME COLUMN_NAME ROW_ID ---------- ---------- -------------------- T1 COL2 AAAWmUAAJAAAF6WAAA T1 COL4 AAAWmUAAJAAAF6WAAA 上述查询给出了列名称和有问题记录的rowid.有了rowid在手,找到那些引起约束违规的记录,修复它们,再次重新启用约束应该没有问题. 以下是用于生成用于启用和禁用约束的alter table语句的脚本: column cons_disable format a50 column cons_enable format a72 select 'alter table ' || t.table_name || ' disable constraint '|| t.constraint_name || ';' as cons_disable,'alter table ' || t.table_name || ' enable constraint '|| t.constraint_name || ' exceptions into exceptions;' as cons_enable from user_constraints t where t.table_name = 'T1' order by t.constraint_type (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |