2012-01-26 23 views
1

私のOracleデータベースのvarchar2列のORDER_PARTS_LISTにコロンで区切られた値のリストがあります。Oracle APEXデータベース・トリガー - データベース列の参照に関する問題

は(私はこのようなリストにデータを格納することはベストプラクティスではないかもしれないということが、今ちょうどその事実を無視するために理解しています。)ここで

は、関連するテーブルのカラムです:

ORDER_TABLE(
    ORDER_NUMBER number, 
    ORDER_PARTS_LIST varchar(4000)) 

PARTS_TABLE(
    PART_NUMBER varchar(20), 
    ASSIGNED_ORDER_NUMBER number) 

I条件付きのトリガーを持っている:

create or replace trigger "ORDER_PARTS_T1" 
BEFORE 
insert or update or delete on "ORDER_TABLE" 
for each row 
begin 
    if :new.ORDER_PARTS_LIST LIKE '%'+PART_NUMBER+'%' then 
    update PARTS_TABLE set ASSIGNED_ORDER_NUMBER = :ORDER_NUMBER; 
    end if; 

end; 

私はこのトリガを実行すると、私は次のエラーを取得する:

0123何が起こることになっているが、トリガチェックがどの PART_NUMBERsPARTS_TABLEに、 ORDER_TABLEで、 ORDER_PARTS_LISTに含まれ、そしてその後​​カラムに、 ORDER_TABLEで影響を受けた行に対して、 ORDER_NUMBERを挿入することである
PLS-00201: identifier 'PART_NUMBER' must be declared 

PARTS_TABLEです。

最後に、ORDER内のすべてのPARTSにそのORDERのNUMBERでフラグを付けます。

これは意味がありますか?

私はこのトリガの変数を正しく定義して実行するようにしているとは確信していません。正直なところ、トリガが働いていてもそれを実行するかどうかは疑問があります。私がそれを定義したように、トリガの機能を得るための提案や助けはすばらしいはずです。前もって感謝します。このすべてが一緒にどのように適合するか

答えて

1

あなたは各行をテストするために一致する文字列を行うことができます。ORDER_PARTS_LISTが'123:456:789'ある場合

create or replace trigger "ORDER_PARTS_T1" 
BEFORE 
insert or update on "ORDER_TABLE" 
for each row 
begin 
    update PARTS_TABLE p 
    set p.ASSIGNED_ORDER_NUMBER = :new.ORDER_NUMBER 
    where instr(':' || :new.ORDER_PARTS_LIST || ':' 
      ,':' || p.PART_NUMBER || ':') > 0; 
end; 

したがって、例えば、INSTR 124 IDS 123、456及び789の一致を見つけることではなくなります、45または例えば、図8に示す。

部品が順から削除された場合、あなたがPARTS_TABLENULL適切なフィールドに別のトリガーが必要になります。

create or replace trigger "ORDER_PARTS_T1" 
BEFORE 
update on "ORDER_TABLE" 
for each row 
begin 
    update PARTS_TABLE p 
    set p.ASSIGNED_ORDER_NUMBER = NULL 
    where instr(':' || :new.ORDER_PARTS_LIST || ':' 
      ,':' || p.PART_NUMBER || ':') = 0 
    and instr(':' || :old.ORDER_PARTS_LIST || ':' 
      ,':' || p.PART_NUMBER || ':') > 0; 
end; 
+0

ありがとうございました!チャームのように働いた! – Spags

+0

ちょっとしたフォローアップのように、あなたは削除を言及しました。私はあなたが正しいと思うのですが、レコードがデータベースから削除されない可能性があるので、それが本当に含まれている理由はありません。ただし、処理のためにPART_NUMBERSを送信する前に、PART_NUMBERSをORDERから削除する可能性があります。パーツが注文から削除された場合、PARTS_TABLEを簡単に更新する方法はありますか? OLD&NEWなどを使用して別のトリガーが必要ですか? – Spags

+0

多分 - 私は提案で私の答えを編集しました。 –

-1

全くわからない(複数のご注文で同じ部分を考慮しています。このように思える)、しかし、あなたが何をしようとしているが、このようなものであるように見えます:

create or replace trigger "ORDER_PARTS_T1" 
BEFORE 
insert or update or delete on "ORDER_TABLE" 
for each row 
begin 
    update parts_table 
    set assigned_order_number = :new.ORDER_NUMBER 
    where part_number in (:new.order_parts_list); 
end; 
+0

うーん...一つだけPART_NUMBERが選択されている場合に動作するようだが、倍数を持っている場合選択されていません。それはエラーをスローしませんが、それだけで値を記述しません。 – Spags

+0

@ Danimal37、残念ながら、INステートメントが魔法のように単一のパラメータ( ':new。order_parts_list')をあなたが期待するかもしれないイン・リストに追加します。そのため、1つの値しか選択されていない場合にのみ機能します。 –

+0

右...おそらく、正しく動作するには、各要素を一重引用符で囲む必要があります。 –

0

ORDER_TABLEにトリガーを作成しています。 ORDER_TABLEにはPART_NUMBERという名前の列が含まれていないため、OracleはPARTS_TABLEに属しているため、識別子 'PART_NUMBER'を見つけることができません。

PARTS_TABLEのPART_NUMBERにアクセスするには、トリガーに別のクエリを記述する必要があります。

関連する問題