在Oracle脚本中使用开始- End语句激活和停用触发器

g6baxovj  于 2023-10-16  发布在  Oracle
关注(0)|答案(2)|浏览(93)

我需要在执行脚本中的一些请求之前停用触发器:

DECLARE
    CPM_ID PLS_INTEGER;
    CPM_ID_TO_DELETE PLS_INTEGER;
BEGIN
    BEGIN
        SELECT ID INTO CPM_ID_TO_DELETE FROM CPM_T WHERE TITLE LIKE '%My Contract%';
        DELETE CPM_HIST_T WHERE HIST_ID  = CPM_ID_TO_DELETE;
        -- Deactivate the trigger
        EXECUTE IMMEDIATE 'ALTER TRIGGER CPM_HIST_ID_TRIG DISABLE';
        DELETE CPM_T WHERE ID  = CPM_ID_TO_DELETE;
        -- Activate the trigger
        EXECUTE IMMEDIATE 'ALTER TRIGGER CPM_HIST_ID_TRIG ENABLE';
    EXCEPTION
        WHEN NO_DATA_FOUND
            THEN
                NULL;
    END;
    CPM_ID := CPM_ID_SEQ.nextval;
    Insert into CPM_T (ID,ORG_ID,TITLE) values (CPM_ID,'7257','My Contract');
END;

然而,它不工作,我得到这个错误:“通常是PL/SQL编译错误- ORA-06550”
我无法执行命令“ALTER......”。
你能帮我解决这个问题吗?

kiayqfof

kiayqfof1#

“通常”是什么意思有时,但不总是?因为,您发布的代码看起来很好,并且不会在我的测试用例中引发错误。
示例对象:

SQL> CREATE TABLE cpm_t
  2  (
  3     id       NUMBER,
  4     org_id   VARCHAR2 (20),
  5     title    VARCHAR2 (20)
  6  );

Table created.

SQL> CREATE TABLE cpm_hist_t
  2  (
  3     hist_id   NUMBER
  4  );

Table created.

SQL> CREATE OR REPLACE TRIGGER cpm_hist_id_trig
  2     BEFORE INSERT
  3     ON cpm_hist_t
  4     FOR EACH ROW
  5  BEGIN
  6     NULL;
  7  END;
  8  /

Trigger created.

SQL> CREATE SEQUENCE cpm_id_seq;

Sequence created.

您的代码(转换为过程;我什么都没改):

SQL> CREATE OR REPLACE PROCEDURE p_test
  2  AS
  3     cpm_id            PLS_INTEGER;
  4     cpm_id_to_delete  PLS_INTEGER;
  5  BEGIN
  6     BEGIN
  7        SELECT id
  8          INTO cpm_id_to_delete
  9          FROM cpm_t
 10         WHERE title LIKE '%My Contract%';
 11
 12        DELETE cpm_hist_t
 13         WHERE hist_id = cpm_id_to_delete;
 14
 15        -- Deactivate the trigger
 16        EXECUTE IMMEDIATE 'ALTER TRIGGER CPM_HIST_ID_TRIG DISABLE';
 17
 18        DELETE cpm_t
 19         WHERE id = cpm_id_to_delete;
 20
 21        -- Activate the trigger
 22        EXECUTE IMMEDIATE 'ALTER TRIGGER CPM_HIST_ID_TRIG ENABLE';
 23     EXCEPTION
 24        WHEN NO_DATA_FOUND
 25        THEN
 26           NULL;
 27     END;
 28
 29     cpm_id := cpm_id_seq.NEXTVAL;
 30
 31     INSERT INTO cpm_t (id, org_id, title)
 32          VALUES (cpm_id, '7257', 'My Contract');
 33  END;
 34  /

Procedure created.

测试:

SQL> EXEC p_test;

PL/SQL procedure successfully completed.

SQL> SELECT * FROM cpm_t;

        ID ORG_ID               TITLE
---------- -------------------- --------------------
         1 7257                 My Contract

SQL> SELECT * FROM cpm_t;

        ID ORG_ID               TITLE
---------- -------------------- --------------------
         2 7257                 My Contract

SQL>

所以,没什么问题。
您能否发布自己的SQL*Plus会话来说明问题?

8fq7wneg

8fq7wneg2#

您的代码似乎可以正常工作(如果您使用SQL*Plus、SQL Developer等)。然后你需要在PL/SQL块的末尾的新行上添加一个PL/SQL终止符/)。
你可以(取决于你的触发器做什么)重写它:

DECLARE
  CPM_ID_TO_DELETE CPM_T.ID%TYPE;
BEGIN
  BEGIN
    -- Deactivate the trigger
    EXECUTE IMMEDIATE 'ALTER TRIGGER CPM_HIST_ID_TRIG DISABLE';

    DELETE CPM_T
    WHERE TITLE LIKE '%My Contract%'
    RETURNING ID INTO CPM_ID_TO_DELETE;

    DELETE CPM_HIST_T WHERE HIST_ID  = CPM_ID_TO_DELETE;

    -- Activate the trigger
    EXECUTE IMMEDIATE 'ALTER TRIGGER CPM_HIST_ID_TRIG ENABLE';
  EXCEPTION
    WHEN NO_DATA_FOUND THEN
      NULL;
  END;
  Insert into CPM_T (ID,ORG_ID,TITLE) values (CPM_ID_SEQ.nextval,'7257','My Contract');
END;
/

fiddle

相关问题