如何从不同模式的触发器调用另一个模式的过程
How do I call a procedure of another schema from the trigger of a different schema
我正在尝试创建一个触发器来记录特定架构 (Schema DS) 的所有 ddl 更改并在另一个架构 (Schema SD) 中更新这些更改。
CREATE OR REPLACE TRIGGER audit_ddl_trg AFTER DDL ON SCHEMA DECLARE
sql_text ora_name_list_t;
v_stmt VARCHAR2(2000);
n PLS_INTEGER;
BEGIN
n := ora_sql_txt(sql_text);
FOR i IN 1..n LOOP v_stmt := v_stmt || sql_text(i);
END LOOP;
v_stmt := regexp_replace(v_stmt, 'rename[[:space:]]+.*[[:space:]]+to[[:space:]]+([a-z0-9_]+)', '', 1, 1,
'i');
IF ( ora_sysevent = 'TRUNCATE' ) THEN
NULL;
ELSE
INSERT INTO audit_ddl (
d,
osuser,
current_user,
host,
terminal,
owner,
type,
name,
sysevent,
statements
) VALUES (
sysdate,
sys_context('USERENV', 'OS_USER'),
sys_context('USERENV', 'CURRENT_USER'),
sys_context('USERENV', 'HOST'),
sys_context('USERENV', 'TERMINAL'),
ora_dict_obj_owner,
ora_dict_obj_type,
ora_dict_obj_name,
ora_sysevent,
v_stmt
);
sd.insert_log(sql_text);
END IF;
END;
/
但是,程序好像不认识。我尝试创建一个数据库 link。但这也行不通。有没有办法解决这个问题?
我怀疑您在一个模式中有触发器,在另一个模式中有 table,但我不知道哪个是哪个。假设 AUDIT_DDL_TRIG
在架构 DS
中,table AUDIT_DDL
在架构 SD
中。在这种情况下,您需要使用 table 所在的模式来限定 table 的名称,即 INSERT INTO SD.AUDIT_DDL(...whatever...)
。此外,架构 DS
将需要具有适当的 GRANT,以便它可以将数据存储到 table 中,如 GRANT INSERT INTO SD.AUDIT_DLL TO DS
.
编辑
如果问题出在过程结束时对 SD.INSERT_LOG
的调用,您可能需要授予对架构 DS
:
的执行权限
GRANT EXECUTE ON SD.INSERT_LOG TO DS;
我正在尝试创建一个触发器来记录特定架构 (Schema DS) 的所有 ddl 更改并在另一个架构 (Schema SD) 中更新这些更改。
CREATE OR REPLACE TRIGGER audit_ddl_trg AFTER DDL ON SCHEMA DECLARE
sql_text ora_name_list_t;
v_stmt VARCHAR2(2000);
n PLS_INTEGER;
BEGIN
n := ora_sql_txt(sql_text);
FOR i IN 1..n LOOP v_stmt := v_stmt || sql_text(i);
END LOOP;
v_stmt := regexp_replace(v_stmt, 'rename[[:space:]]+.*[[:space:]]+to[[:space:]]+([a-z0-9_]+)', '', 1, 1,
'i');
IF ( ora_sysevent = 'TRUNCATE' ) THEN
NULL;
ELSE
INSERT INTO audit_ddl (
d,
osuser,
current_user,
host,
terminal,
owner,
type,
name,
sysevent,
statements
) VALUES (
sysdate,
sys_context('USERENV', 'OS_USER'),
sys_context('USERENV', 'CURRENT_USER'),
sys_context('USERENV', 'HOST'),
sys_context('USERENV', 'TERMINAL'),
ora_dict_obj_owner,
ora_dict_obj_type,
ora_dict_obj_name,
ora_sysevent,
v_stmt
);
sd.insert_log(sql_text);
END IF;
END;
/
但是,程序好像不认识。我尝试创建一个数据库 link。但这也行不通。有没有办法解决这个问题?
我怀疑您在一个模式中有触发器,在另一个模式中有 table,但我不知道哪个是哪个。假设 AUDIT_DDL_TRIG
在架构 DS
中,table AUDIT_DDL
在架构 SD
中。在这种情况下,您需要使用 table 所在的模式来限定 table 的名称,即 INSERT INTO SD.AUDIT_DDL(...whatever...)
。此外,架构 DS
将需要具有适当的 GRANT,以便它可以将数据存储到 table 中,如 GRANT INSERT INTO SD.AUDIT_DLL TO DS
.
编辑
如果问题出在过程结束时对 SD.INSERT_LOG
的调用,您可能需要授予对架构 DS
:
GRANT EXECUTE ON SD.INSERT_LOG TO DS;