PLS-00049: 错误的绑定变量 'X_VARIABLE'

PLS-00049: bad bind variable 'X_VARIABLE'

当我尝试从 table 获取记录时出现以下错误,在本例中,是 (SERVICIOENDIAS)/SERVICETIMEINDAYS 我不知道为什么会出现该错误:

触发TRG_CONTROL_SERVICIO编译

LINE/COL  ERROR
--------- -------------------------------------------------------------
20/11     PLS-00049: bad bind variable 'NEW.V_SERVICIODIAS'
Errors: check compiler log
 

我是 Oracle 的傻瓜,我可能会犯很多错误和不良做法,所以如果你能告诉我,我将不胜感激。

  CREATE OR REPLACE TRIGGER TRG_CONTROL_SERVICIO
BEFORE
INSERT OR UPDATE
ON SERVICIO
FOR EACH ROW

DECLARE
V_SERVICIODIAS INT;

CURSOR C_SERVICIODIAS IS 
    SELECT TIEMPOSERVICIODIAS INTO V_SERVICIODIAS
    FROM SERVICIO;
BEGIN
FOR R_SERVICIODIAS IN C_SERVICIODIAS LOOP
    IF INSERTING THEN
        IF :NEW.FECHAREGISTRO > SYSDATE THEN
               LOG_AUDIT( USER, 
                          SYSDATE, 
                          'SERVICIO', 
                          'INSERT FECHA INCORRECTA', 
                          'SE EJECUTO EL TRG_CONTROL_SERVICIO'); 
               RAISE_APPLICATION_ERROR(-20000, 'FECHA INCORRECTA, INTENTE DE NUEVO');
       ELSE
          DBMS_OUTPUT.PUT_LINE('INSERTANDO UN SERVICIO');
       END IF;
       IF :NEW.V_SERVICIODIAS <= 60 THEN
        DBMS_OUTPUT.PUT_LINE('INSERTANDO UN SERVICIO');
       ELSE
          LOG_AUDIT( USER, 
                          SYSDATE, 
                          'SERVICIO', 
                          'NO SE PUEDE UN SERVICIO MAYOR A 60 DIAS', 
                          'SE EJECUTO EL TRG_CONTROL_SERVICIO'); 
          RAISE_APPLICATION_ERROR(-20000, 'NO SE PUEDE REGISTRAR EL SERVICIO, MUCHAS HORAS',TRUE);
       END IF;
    ELSIF UPDATING THEN
        IF :NEW.FECHAREGISTRO <> :OLD.FECHAREGISTRO AND :NEW.FECHAREGISTRO > SYSDATE THEN
                 LOG_AUDIT( USER, 
                          SYSDATE, 
                          'SERVICIO', 
                          'PROHIBIDO UPDATE FECHAREGISTRO',
                          'SE EJECUTO EL TRG_CONTROL_SERVICIO'); 
              RAISE_APPLICATION_ERROR(-20000, 'FECHA INCORRECTA, NO SE PUEDE MODIFICAR ESTA FECHA',TRUE);
    ELSE
        DBMS_OUTPUT.PUT_LINE('ACTUALIZANDO UN EMPLEADO');
    END IF;
END IF;
END LOOP;
END;

在你的程序中V_SERVICIODIAS INT;是一个声明的变量,所以你必须在语法上把它当作一个变量来使用。

正确的if语句如下,请尝试使用:

IF V_SERVICIODIAS <= 60 THEN

如前所述,V_SERVICIODIAS 是一个局部变量,因此它不是 :NEW 伪记录的一部分。你会用

IF V_SERVICIODIAS <= 60 THEN

一旦你这样做了,下一个问题就是实际上没有任何东西填充那个局部变量,所以 if 语句永远不会为真。那是因为您的游标定义中存在语法错误。如果你有一个 select 语句 returns 单行而不是当你定义一个你计划循环的游标时,你使用 into 子句

CURSOR C_SERVICIODIAS IS 
    SELECT TIEMPOSERVICIODIAS 
    FROM SERVICIO;

修复游标定义错误后,您将完全摆脱局部变量并仅引用游标中的列。

IF R_SERVICIODIAS.TIEMPOSERVICIODIAS <= 60 THEN

然而,完成所有这些后,您将遇到变异的 table 运行时错误,因为 SERVICIO 上的行级游标将无法查询SERVICIOtable。而且,不幸的是,到那时还不清楚如何解决问题,因为光标最初存在的原因并不明显。为什么每次在 table 中插入新行时都要遍历 table 中的每一行?这真的没有任何意义。

一种可能是您实际上不想遍历 table 中的每一行。也许您想删除 V_SERVICIODIAS 局部变量和游标定义以及循环,并只引用当前行中的 TIEMPOSERVICIODIAS

IF :NEW.TIEMPOSERVICIODIAS <= 60 THEN