Oracle DBMS INSERT过程无效

时间:2014-04-10 12:46:34

标签: sql oracle stored-procedures

我正在研究数据库的简单功能。

当用户注册我的应用程序时,字段password_changed初始化为0,在我的user trigger中执行此操作后,我想触发以下方法向该新用户发送一条消息告诉他们他们应该更新密码。

CREATE OR REPLACE TRIGGER trg_users
BEFORE INSERT OR UPDATE ON users FOR EACH ROW
BEGIN
    -- Get the new user id
    IF :NEW.user_id IS NULL THEN
        SELECT seq_user_id.nextval
        INTO :NEW.user_id
        FROM sys.dual;
    END IF;

   -- Alert a user that they need to change their password
   IF :NEW.pass_changed IS NULL THEN
      :NEW.pass_changed := 0;
      send_alert(:NEW.user_id, 'Thank-you for registering, please change your password for security reasons!');
   END IF;
END;

这个第一个触发器只是初始化设置为0的密码,然后调用我的send_alert()函数,获取由我的序列填充的:NEW.user_id

send_alert()程序:

-- Sends an alert to the user noting that they haven't changed their password
CREATE OR REPLACE PROCEDURE send_alert( 
   this_user users.user_id%TYPE, 
   this_message STRING 
)
AS
BEGIN
   INSERT INTO messages 
   VALUES('', this_user, getSystemId(), 'ALERT', this_message, '', '');
END send_alert;

当此代码运行时,我收到错误integrity constraint (PRCSE.INBOX_MESSAGE_TO_FK) violated - parent key not found我理解这意味着什么 - 但是如果我用该字段替换现有值,则应通过this_user填充父键的值。程序完成,旧用户INSERTS

我只能认为由于某种原因:NEW.user_id没有通过,但我在调用我的程序之前初始化它的值。

EDIT 10/04/14 13:48 GMT :要清除任何混淆,getSystem()会返回主管理员ID

-- Gets the ID of the SYSTEM user via its unique email
CREATE OR REPLACE FUNCTION getSystemId 
    RETURN NUMBER
IS
    system_user users.user_id%TYPE;
    pragma autonomous_transaction;
BEGIN 
    SELECT user_id
    INTO   system_user
    FROM   users
    WHERE  user_email = 'system@application.com'
    AND    user_permissions = 'ADMIN';
RETURN system_user;
COMMIT;
END getSystemId;

任何帮助将不胜感激 - 此致,Alex。

1 个答案:

答案 0 :(得分:2)

这是因为您尝试在BEFORE触发器中插入值(例如,在插入父行之前):

SQL> create table t(x int primary key);


SQL> create table t_c(x int references t(x));


SQL> create or replace trigger tr_i
  2  before insert on t
  3  for each row
  4  begin
  5    insert into t_c(x) values(:new.x);
  6  end;
  7  /

SQL> insert into t values(1);
insert into t values(1)
            *
error in line 1:
ORA-02291: integrity constraint (SCOTT.SYS_C00330529) voilated - parent key not found
ORA-06512: in  "SCOTT.TR_I", line 2 
ORA-04088: error in trigger execution 'SCOTT.TR_I' 


SQL> create or replace trigger tr_i
  2  after insert on t
  3  for each row
  4  begin
  5    insert into t_c(x) values(:new.x);
  6  end;
  7  /

SQL> insert into t values(1);

1 row inserted.

SQL> select * from t;

     X                                                                          
------                                                                          
     1                                                                          

SQL> select * from t_c;

     X                                                                          
------                                                                          
     1