Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/windows/15.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Oracle 具有动态SQL的PL/SQL触发器_Oracle_Plsql_Triggers - Fatal编程技术网

Oracle 具有动态SQL的PL/SQL触发器

Oracle 具有动态SQL的PL/SQL触发器,oracle,plsql,triggers,Oracle,Plsql,Triggers,我想创建ddl触发器(在创建时),它将创建一个dml触发器 但我有一个错误: ORA-06512:8号线 60400000-“递归SQL级别%s发生错误” *原因:处理递归SQL语句时出错 (适用于内部字典表的语句)。 *措施:如果出现堆栈上下一个错误中描述的情况 可以纠正的,就这样做;否则请与Oracle支持部门联系 至少,我希望你希望new.time.成为:new.time.至少,我希望你希望new.time.成为:new.time.你在结束后缺少一个分号 替换这个 EXECUTE IMME

我想创建ddl触发器(在创建时),它将创建一个dml触发器 但我有一个错误:

ORA-06512:8号线 60400000-“递归SQL级别%s发生错误” *原因:处理递归SQL语句时出错 (适用于内部字典表的语句)。 *措施:如果出现堆栈上下一个错误中描述的情况 可以纠正的,就这样做;否则请与Oracle支持部门联系


至少,我希望你希望
new.time.
成为
:new.time.
至少,我希望你希望
new.time.
成为
:new.time.
你在
结束后缺少一个分号

替换这个

EXECUTE IMMEDIATE 'CREATE OR REPLACE TRIGGER add_user_time BEFORE INSERT OR UPDATE ON test_tab FOR EACH ROW BEGIN ' || ':' || 'new.time_ := sysdate; END';
有了这个

EXECUTE IMMEDIATE 'CREATE OR REPLACE TRIGGER add_user_time BEFORE INSERT OR UPDATE ON test_tab FOR EACH ROW BEGIN ' || ':' || 'new.time_ := sysdate; END;';
完整的错误消息包括:

ORA-00604: error occurred at recursive SQL level 1
ORA-24344: success with compilation error
ORA-06512: at line 8
重要部分是:

ORA-24344: success with compilation error
源代码应为:

CREATE OR REPLACE TRIGGER test_ddl
after CREATE ON SCHEMA
DECLARE 
    user_col VARCHAR(5) := 'user_';
    time_col VARCHAR(5) := 'time_';
BEGIN
IF ora_dict_obj_type = 'TABLE'
THEN 
    EXECUTE IMMEDIATE 'alter table ' || ora_dict_obj_name || ' add(' || user_col || ' varchar(20), '|| time_col ||' timestamp)'||'';
    EXECUTE IMMEDIATE 'CREATE OR REPLACE TRIGGER add_user_time BEFORE INSERT OR UPDATE ON test_tab FOR EACH ROW BEGIN ' || ':' || 'new.time_ := sysdate; END;';
END IF;
END;                               
/
DROP TABLE test_tab PURGE;
/
CREATE TABLE test_tab(ID NUMBER);

作为一种解释:我放了一些日志消息来查看它到底在哪里失败。然后,您可以看到在
创建或替换触发器
时递归调用触发器,但使用
命令对象类型
=
触发器
则在
结束
后缺少分号

替换这个

EXECUTE IMMEDIATE 'CREATE OR REPLACE TRIGGER add_user_time BEFORE INSERT OR UPDATE ON test_tab FOR EACH ROW BEGIN ' || ':' || 'new.time_ := sysdate; END';
有了这个

EXECUTE IMMEDIATE 'CREATE OR REPLACE TRIGGER add_user_time BEFORE INSERT OR UPDATE ON test_tab FOR EACH ROW BEGIN ' || ':' || 'new.time_ := sysdate; END;';
完整的错误消息包括:

ORA-00604: error occurred at recursive SQL level 1
ORA-24344: success with compilation error
ORA-06512: at line 8
重要部分是:

ORA-24344: success with compilation error
源代码应为:

CREATE OR REPLACE TRIGGER test_ddl
after CREATE ON SCHEMA
DECLARE 
    user_col VARCHAR(5) := 'user_';
    time_col VARCHAR(5) := 'time_';
BEGIN
IF ora_dict_obj_type = 'TABLE'
THEN 
    EXECUTE IMMEDIATE 'alter table ' || ora_dict_obj_name || ' add(' || user_col || ' varchar(20), '|| time_col ||' timestamp)'||'';
    EXECUTE IMMEDIATE 'CREATE OR REPLACE TRIGGER add_user_time BEFORE INSERT OR UPDATE ON test_tab FOR EACH ROW BEGIN ' || ':' || 'new.time_ := sysdate; END;';
END IF;
END;                               
/
DROP TABLE test_tab PURGE;
/
CREATE TABLE test_tab(ID NUMBER);

作为一种解释:我放了一些日志消息来查看它到底在哪里失败。然后您可以看到,触发器在
创建或替换触发器
时被递归调用,但问题不在这里。问题是我不能在其他触发器中创建触发器是的,我错过了。问题不在这里。一个问题是我不能在其他触发器中创建触发器是的,我错过了。你可能想做一些日志记录,至少要记录生成和执行的DDL语句。您的触发器创建语句似乎是用触发器和表的单一名称硬编码的-这可能是原因,也可能不是原因。添加一个记录错误的异常处理程序(在重新引发错误之前)可能会有所帮助。请注意,当创建触发器时,此触发器将以递归方式触发(当然,由于ora_dict_obj_type上的条件,您的代码会停止递归触发器实际执行任何操作)。您可能希望执行一些日志记录,至少是生成和执行的DDL语句。您的触发器创建语句似乎是用触发器和表的单一名称硬编码的-这可能是原因,也可能不是原因。添加一个记录错误的异常处理程序(在重新引发错误之前)可能会有所帮助。请注意,当创建触发器时,此触发器将以递归方式触发(当然,由于ora_dict_obj_type上的条件,您的代码会停止递归触发器实际执行任何操作)。在模式上创建后创建或替换触发器test_ddl DECLARE user_col VARCHAR(5):=“user_u”;time_col VARCHAR(5):=“time_”;如果ora|U dict|U obj|U type='TABLE',则立即执行'alter TABLE'| ora|U dict|U obj|U name | |'add('| | user| U col | |'varchar(20),'| | time| col | |'timestamp');在插入或更新“| | ora|dict_obj_name | |”或“ora|dict_obj_name | |”之前,对每行开始“| |”执行立即“创建或替换触发器添加_user_time”:“| |”new.time:=sysdate;"完";;如果结束;结束;创建表测试选项卡(ID号);在模式上创建后创建或替换触发器测试\u ddl DECLARE user\u col VARCHAR(5):=“user_u”;time_col VARCHAR(5):=“time_”;如果ora|U dict|U obj|U type='TABLE',则立即执行'alter TABLE'| ora|U dict|U obj|U name | |'add('| | user| U col | |'varchar(20),'| | time| col | |'timestamp');在插入或更新“| | ora|dict_obj_name | |”或“ora|dict_obj_name | |”之前,对每行开始“| |”执行立即“创建或替换触发器添加_user_time”:“| |”new.time:=sysdate;"完";;如果结束;结束;创建表测试选项卡(ID号);