存储过程:仅在成功时提交

时间:2017-03-07 09:51:32

标签: sql oracle stored-procedures commit

我想构建一个存储过程: 1.截断表A. 2.截断表B. 3.在表A中插入(大量)行 4.在表B中插入(大量)行

存储过程应仅在步骤4之后提交语句,以便表不会被锁定并且不会遇到停机时间。 如果发生错误(例如,在步骤4中),则必须回滚所有更改。我自己尝试写这篇文章,但是在每次发言之后都做了。

create or replace PROCEDURE upall as

BEGIN
  execute immediate 'truncate table MAIN.SET';
  insert into MAIN.SET select * from MAIN.SET_STAG;

  execute immediate 'truncate table MAIN.TYPE';
  insert into MAIN.TYPE select * from MAIN.TYPE_STAG;

  COMMIT; 
EXCEPTION WHEN OTHERS THEN
  ROLLBACK;
  RAISE; 
END;

1 个答案:

答案 0 :(得分:5)

在Oracle中,TRUNCATE TABLE是一个DDL语句,不能在事务中使用(或者,更准确地说,不能回滚)。如果在执行语句时正在进行事务,则提交事务然后提交TRUNCATE已执行且无法撤消。

尝试DELETE FROM YourTable并最终更新您的表的统计信息(因为DELETE将过期)

看起来像是:

CREATE or REPLACE PROCEDURE upall as

BEGIN
    delete from MAIN.SET;
    insert into MAIN.SET select * from MAIN.SET_STAG;

    delete from MAIN.TYPE;
    insert into MAIN.TYPE select * from MAIN.TYPE_STAG;

    COMMIT; 

    EXEC DBMS_STATS.GATHER_TABLE_STATS ('MAIN', 'SET');
    EXEC DBMS_STATS.GATHER_TABLE_STATS ('MAIN', 'TYPE');

    EXCEPTION WHEN OTHERS THEN
    ROLLBACK;
    RAISE; 
END;