PL / SQL为什么我在触发操作上获得DEADLOCK?

时间:2016-11-13 14:11:13

标签: plsql database-connection deadlock dml database-trigger

我有以下触发器

    CREATE OR REPLACE TRIGGER LAST_EDIT 
    BEFORE UPDATE ON MESSAGES
    FOR EACH ROW
    DECLARE
    pragma autonomous_transaction;
    BEGIN
     if :NEW.TEXT <> :OLD.TEXT THEN
      UPDATE MESSAGES set MESSAGES.LAST_EDITED=(select USERS.EMAIL from USERS inner join LAST_EDITED_TABLE on users.ID=LAST_EDITED_TABLE.USER_ID  where 
      LAST_EDITED_TABLE.MESSAGE_ID=(select MESSAGE_ID from LAST_EDITED_TABLE where DATE_MESSAGE=(select max(DATE_MESSAGE) from LAST_EDITED_TABLE )));
    ENDIF;
COMMIT;
END;

我收到以下错误

ORA-06512: at "DIP.MESSAGEPACKAGE", line 35
00060. 00000 -  "deadlock detected while waiting for resource"
*Cause:    Transactions deadlocked one another while waiting for resources.
*Action:   Look at the trace file to see the transactions and resources
           involved. Retry if necessary

我试图更新说明谁进行最后更新的行(来自同一个表的一行)。有人可以帮帮我吗?

1 个答案:

答案 0 :(得分:1)

这不是你真正需要的吗?

CREATE OR REPLACE TRIGGER LAST_EDIT 
BEFORE UPDATE ON MESSAGES
FOR EACH ROW
DECLARE
  email USERS.EMAIL%type;
BEGIN     
 if :NEW.TEXT <> :OLD.TEXT THEN
  select USERS.EMAIL into email 
    from USERS inner join LAST_EDITED_TABLE on users.ID=LAST_EDITED_TABLE.USER_ID  
     where LAST_EDITED_TABLE.MESSAGE_ID = (select MESSAGE_ID from LAST_EDITED_TABLE where DATE_MESSAGE = (select max(DATE_MESSAGE) from LAST_EDITED_TABLE ));
  :NEW.LAST_EDITED = email;
END IF;
COMMIT;
END;
/

查询中查找电子邮件的逻辑也太复杂了。当然,你可以简化它。