【问题标题】:PL/SQL: ORA-00904: : invalid identifierPL/SQL: ORA-00904: : 无效标识符
【发布时间】:2014-01-06 23:17:47
【问题描述】:

我正在运行以下 SP,但收到错误 c1.pyid is invalid identifier。我正在尝试使用来自一个游标的两个不同的查询结果。如果有任何其他方式在游标中使用 IF-else 子句,我也对此持开放态度。

 CREATE OR REPLACE
  PROCEDURE FIX_DOCUMENT_RECORDS ( i_flag in varchar)
AS
Op_ID      VARCHAR(8);
Op_Name    VARCHAR(32);
  skill      VARCHAR(32);
temp_count VARCHAR(8);
temp_status VARCHAR(8):='Submitted';
QRYSTR VARCHAR2(400);
TYPE REF_CUR IS REF CURSOR;
 c1 REF_CUR;

BEGIN
 IF (i_flag='1') THEN
 QRYSTR:='SELECT *
FROM dims_doc_master
WHERE concat_prod_id      IS NULL
OR documenttypeid      IS NULL
AND (pystatuswork       = temp_status);';
ELSE
QRYSTR:='SELECT *
FROM dims_doc_master
WHERE (documentimageid IS NULL
AND p8id               IS NULL)
   AND (pystatuswork       = temp_status);';
END IF;   

 open c1 FOR QRYSTR;
LOOP
BEGIN

  DBMS_OUTPUT.PUT_LINE('loop begin');
  UPDATE DIMS_DOC_MASTER
  SET pystatuswork  ='Cancelled',
    documentstatus  ='Cancelled',
    cancellationdate='31-JAN-14',
    cancelledbysid  = c1.pxcreateoperator,
    cancelreason    ='Cancelled due to corruption.'
  WHERE pyid        =c1.pyid;

  DBMS_OUTPUT.PUT_LINE('After updation'||c1.pyid );
  --Begin PC_DOCUMENT UPDATION
  UPDATE PC_DOCUMENT
  SET pystatuswork  ='Cancelled',
    cancellationdate='31-JAN-14'
  WHERE pyid        =c1.pyid;
  --Begin insert into History
  --Select Operator name and ID

  SELECT skill
  INTO skill
  FROM operator_map_skill
  WHERE pyuseridentifier=c1.pxcreateoperator
  AND rownum            =1;
  INSERT
  INTO DIMS_DOC_HIST
    (
      DIMS_DOC_ID,
      DOC_CHG_USR,
      DOC_CHG_DT,
      DOC_NEW_STS,
      DOC_CHG_CMNT,
      CRE_TS,
      ROLE,
      RSN_DESC,
      TARGETROLE,
      DOC_CHG_USR_ID,
      DOC_ASG_USR_ID,
      DOC_ASG_USR,
      PREVSTATUS,
      PREVSTATUSDT,
      ASSIGNEDTODT,
      TODISPLAY,
      ACTIVITY_NAME
    )
    VALUES
    (
      c1.pyid,
      'DIMS',
      systimestamp,
      'Cancelled',
      'Cancelled due to corruption',
      '31-JAN-14',
      skill,
      NULL,
      skill,
      c1.pxcreateoperator,
      c1.pxcreateoperator,
      c1.pxcreateopname,
      'Submitted',
      NULL,
      systimestamp,
      'Y',
      'Updation through Script'
    );

  dbms_output.put_line
  (
    'Document ID= '||c1.pyid
  )
  ;
  SELECT COUNT(*)
  INTO temp_count
  FROM PC_ASSIGN_WORKBASKET
  WHERE pxrefobjectinsname=c1.pyid;
  IF(temp_count          IS NOT NULL) THEN
    DELETE FROM PC_ASSIGN_WORKBASKET WHERE pxrefobjectinsname=c1.pyid;
  ELSE
    DELETE FROM PC_ASSIGN_WORKLIST WHERE pxrefobjectinsname=c1.pyid;
  END IF;
  COMMIT;
END;
END LOOP;
 CLOSE c1;

END;  

【问题讨论】:

  • 嗨,我看到c1.pyid 在您的程序中被多次使用。错误发生在哪一行(例如使用SELECT * FROM USER_ERRORS)?顺便说一句,您能否删除问题中的所有注释代码?它会更容易阅读和理解。
  • 错误是针对所有 c1.pyid。表 dims_doc_master 有一个列名 pyid,所以理想情况下光标应该从那里拾取它。我已经删除了注释代码。
  • 您应该从中得到PLS-00487: Invalid reference to variable 'C1'。奇怪。

标签: sql database oracle stored-procedures oracle11g


【解决方案1】:

尝试在 where 子句中嵌入标志:

open c1 FOR 
SELECT *
FROM dims_doc_master
WHERE (i_flag='1' AND 
      (concat_prod_id      IS NULL
    OR documenttypeid      IS NULL
   AND (pystatuswork       = temp_status))
OR (i_flag<>'1' AND
      (documentimageid IS NULL
   AND p8id               IS NULL)
   AND (pystatuswork       = temp_status));

逻辑可能可以简化,但逻辑上可行。

【讨论】:

  • 我进行了您建议的更改,但在 c1 REF_CUR 之后它给了我一个错误;说期待别的东西时遇到符号“FOR”
【解决方案2】:

您似乎混淆了光标和获取的行。

在您当前的过程中:您打开一个游标,执行一个循环(由于没有 EXIT 语句,这看起来是无穷无尽的),然后在循环之后关闭游标(但它看起来永远不会发生)

要从游标中获取结果,请执行以下操作:

CREATE OR REPLACE PROCEDURE ...
  ...
  c1 REF_CUR; 
  ddm_record dims_doc_master%rowtype; 
BEGIN 
  ...
  OPEN c1;
  LOOP 
     FETCH c1 INTO ddm_record; 
     EXIT WHEN c1%NOTFOUND;
     ...
     DBMS_OUTPUT.PUT_LINE('Document ID= ' || ddm_record.pyid); -- not c1.pyid 
  END LOOP;
  CLOSE c1;
END; 
/ 

灵感来自此处的示例:http://plsql-tutorial.com/plsql-explicit-cursors.htm

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多