rowid在pl / sql块中自动更改

时间:2013-01-23 17:59:24

标签: oracle stored-procedures rowid

create or replace
PROCEDURE PROMOLOG1 AS
CURSOR rule IS SELECT * FROM business_rules; --this table had where conditions to use
TYPE r_cursor IS REF CURSOR;
ruleMatch r_cursor;
row_id VARCHAR2(20);
query_test VARCHAR2(400);

BEGIN
  FOR a IN rule LOOP
    IF a.rule_name != 'Rule1' THEN
      OPEN rulematch FOR 'SELECT rowid FROM cold_promo_log_dup P WHERE EXISTS( SELECT   1 FROM cold_promo_log_dup C WHERE ' || a.condition || ' AND rowid < P.rowid)';
      dbms_output.put_line('matching completed for ' || a.rule_name);
      LOOP
         FETCH ruleMatch INTO row_id;
         EXIT WHEN rulematch%notfound;
         query_test := 'INSERT INTO cold_promo_log_duplicate SELECT * FROM cold_promo_log_dup WHERE rowid = ''' || row_id ||'''' ;
         dbms_output.put_line(query_test);
         --EXECUTE IMMEDIATE 'INSERT INTO cold_promo_log_duplicate SELECT * FROM cold_promo_log_dup WHERE rowid = ''' || row_id || '''';
         INSERT INTO cold_promo_log_duplicate SELECT * FROM cold_promo_log_dup WHERE rowid = row_id ;
         EXECUTE IMMEDIATE 'DELETE FROM cold_promo_log_dup WHERE rowid = ' || row_id;
      END LOOP;
    END IF;
  END LOOP;
END PROMOLOG1;

在oracle中执行上述过程,抛出以下错误:

    Connecting to the database dedupe_preprod.
    ORA-00904: "AAALJBABVAANSZDAAA": invalid identifier
    ORA-06512: at "DEDUPE.PROMOLOG1", line 23
    ORA-06512: at line 2
    matching completed for Rule2
    INSERT INTO cold_promo_log_duplicate SELECT * FROM cold_promo_log_dup WHERE rowid =   'AAALJBABvAANsZDAAA'
    Process exited.
    Disconnecting from the database dedupe_preprod.

当我打印rowid时,它有几个小写字母(AAALJBABvAANsZDAAA),但错误显示所有大写字母(AAALJBABVAANSZDAAA)。 DB中没有带大写的rowid,因此出现错误无效标识符         任何帮助表示赞赏。

2 个答案:

答案 0 :(得分:3)

首先,你的row_id变量应该是ROWID类型而不是varchar2。

其次这是错误:

 EXECUTE IMMEDIATE 'DELETE FROM cold_promo_log_dup WHERE rowid = ' || row_id;

你没有引用它(因此它将rowid视为标识符)。但是你为什么要在动态SQL中运行它?

如果您要保留此动态,则应使用绑定变量,因此不会丢弃共享池并提高性能。

答案 1 :(得分:0)

不要使用rowid进行循环。你这样做:你可以删除该行,并将其插入其他地方。最好的办法是使用DELETE ... RETURNING BULK COLLECT ...,这样你就不需要使用rowid了,你可以使用集合而不是使用一行一行的for循环