0

这个想法是,我想在更新时将记录克隆为CLOB 。为什么要这样做?有两个不同的应用程序A1A2A1依赖于A2。根据A1值,计算A2的值。

A2进程每天只运行一次以计算值,但对于 A1,相关TABLE_NAME中的每个字段每天都可以更改多次,并且没有历史记录。

目的是创建一个历史,它是自动形式的表“ NEW_TABLE ”中的一个 CLOB 字段。

对不起我的英语,但如果有什么不明白的,我可以重写问题

我的代码在这里:


CREATE or REPLACE TRIGGER TRIGGER_NAME
AFTER  UPDATE
   ON TABLE_NAME 
   FOR EACH ROW 

DECLARE
    row_record                  NEW_TABLE%rowtype;
    c_xml                       CLOB;   


    FUNCTION GetXML(a_tablela varchar2, a_key_1 varchar2, a_key_2 varchar2)
      RETURN CLOB
      is
       x_xml CLOB;
    BEGIN      
      select dbms_xmlgen.getxml('select * from '||a_tablela||' where key_1 = '''||a_key_1||''' and key_2 = '''||a_key_2||'''') into x_xml from dual;              
      return x_xml;
    END;
BEGIN

    --** TABLE_NAME Automatically fetches all columns and transforms them to CLOB
    c_xml := GetXML('TABLE_NAME', :new.key_1, :new.key_2);
    if c_xml is not null then 
        row_record.TABLE_NAME :=c_xml; 
    end if;                


    INSERT INTO NEW_TABLE VALUES row_record;


EXCEPTION
   when others then
        raise_application_error(-20000,'ERROR: '||to_char(sqlcode));

END;


现在我得到错误:

ORA-04091 : 表TABLE_NAME正在变异,触发器/函数可能看不到它。

当我通过SELECT语句获得此记录时。

如何在应用的TRIGGER AFTER UPDATE中将行转换为 CLOB ?

谢谢。

4

1 回答 1

1

您不能使用 select 语句的原因是因为您在触发器中,并且表正在更改或“变异”,如错误所述。您可以从此处更新的行中获取数据的唯一方法是使用新旧:

old.column1
new.column1

old 为更新前列的值,new 为更新后的值。
例子:


CREATE or REPLACE TRIGGER TRIGGER_NAME
AFTER  UPDATE
    ON TABLE_NAME 
    FOR EACH ROW 
BEGIN
    l_string := 'This is the old value for column 1: ' || old.column1 || '. This is the new value: ' || new.column1;
    dbms_output.put_line(l_string);
END;

您将无法使用 dbms_xmlgen,因为它使用了一个 select 语句,该语句会引发 mutating error 异常。

我不确定我是否完全理解您要执行的操作,但是您应该能够自己构建CLOB,只需将自己与列名连接即可。像这样:


CREATE or REPLACE TRIGGER TRIGGER_NAME
AFTER  UPDATE
    ON TABLE_NAME 
    FOR EACH ROW 
BEGIN
    l_clob := 'Column1 ' || old.column1 || ', Column2 ' || old.column2; --For as many columns as are in the table
    --Now you have a clob with all the old values, insert it where you want it
END;

然后从那里去。如果你真的想要 XML 格式,你也可以自己做,只需将字符串连接在一起。

于 2013-08-05T15:18:23.340 回答