条件のセットに基づいて値を切り替えようとしていて、UPDATE式のSET句内にネストされたCASE文がある場合、そのカラムは更新されません。UPDATE SET句のネストされたCASE文
単純なCASE式が存在する場合、列は更新されているように見えます。ただし、この例のOVERRIDDEN_CHECK_NUMBERおよびOVERRIDDEN_AMOUNTでは、列は更新されません。
UPDATEのOVERRIDDEN_DATE、OVERRIDDEN_USER_ID、CHECK_NO、およびAMOUNT列は、問題なく更新されています。
このUPDATE文でOVERRIDDEN_CHECK_NUMBERとOVERRIDDEN_AMOUNTが更新されない理由を教えていただけますか?
入れ子にされたCASE文は、UPDATE式のSET句には使用できませんか?
SQL例
UPDATE WAREHOUSE.BANK_STATEMENT_ACTIVITY
SET OVERRIDDEN_CHECK_NO = --(CASE :btn
(CASE WHEN (:btn = '1') THEN CASE WHEN '141973' = '141973' THEN NULL
WHEN '141973' != '999999' THEN LPAD(TRIM(141973), 12, '0')
END
WHEN (:btn = '2') THEN '1740 - Previously Paid Warrant'
ELSE NULL
END),
OVERRIDDEN_AMOUNT = --(CASE :btn
(CASE WHEN (:btn = '1') THEN CASE WHEN 253.20 = 253.20 THEN NULL
WHEN 253.20 != 999.99 THEN LPAD(TRIM(253.20), 12, '0')
END
WHEN (:btn = '2') THEN NULL
ELSE NULL
END),
OVERRIDDEN_DATE = SYSDATE,
OVERRIDDEN_USER_ID = 1009,
CHECK_NO = (CASE :btn
WHEN '1' THEN LPAD(TRIM(999999), 12, '0')
WHEN '2' THEN '142775'
ELSE NULL
END),
AMOUNT = (CASE :btn
WHEN '1' THEN TRIM(78.60)
WHEN '2' THEN TRIM(253.20)
ELSE NULL
END)
WHERE TO_NUMBER(CHECK_NO) = (CASE :btn
WHEN '1' THEN '141973'
WHEN '2' THEN '142775'
ELSE NULL
END)
AND AMOUNT = (CASE :btn
WHEN '1' THEN 78.60
WHEN '2' THEN 253.20
ELSE NULL
END)
AND TRUNC(LOAD_DATE) = (CASE :btn
WHEN '1' THEN TRUNC(LOAD_DATE)
WHEN '2' THEN (SELECT (MAX(LOAD_DATE)) FROM WAREHOUSE.BANK_STATEMENT_ACTIVITY)
ELSE NULL
END)
AND BANKACCTNO = (SELECT LONGDESC
FROM TCMS.COMPLEMENTARY_VALIDATIONS
WHERE TEXTCODE = 'BANKACCT'
AND CODE = 80);
EDIT
働いていた編集者を経て更新クエリを指摘@mathguy logival問題を修正した後。ただし、PL/SQLパッケージでこれを実行すると、表の更新は失敗します。ここで
は更新前である:
彼女は結果の後にある:
彼らは同じです。
これは、実際のパッケージの手順である:
PROCEDURE UpdateBankStatementActivity(btn IN VARCHAR2)
AS
BEGIN
DBMS_OUTPUT.PUT_LINE('UpdateBankStatementActivity - btn: ' || btn);
DBMS_OUTPUT.PUT_LINE('UpdateBankStatementActivity - bsa_rec.OVERRIDDEN_CHECK_NO: ' || bsa_rec.OVERRIDDEN_CHECK_NO || CHR(10) ||
'bsa_rec.OVERRIDDEN_AMOUNT: ' || bsa_rec.OVERRIDDEN_AMOUNT || CHR(10) ||
'bsa_rec.CHECK_NO: ' || bsa_rec.CHECK_NO || CHR(10) ||
'bsa_rec.AMOUNT: ' || bsa_rec.AMOUNT || CHR(10) ||
'bsa_rec.LOAD_DATE:' || bsa_rec.LOAD_DATE);
UPDATE WAREHOUSE.BANK_STATEMENT_ACTIVITY
SET OVERRIDDEN_CHECK_NO = --(CASE :btn
(CASE WHEN (btn = '1') THEN CASE WHEN bsa_rec.OVERRIDDEN_CHECK_NO = bsa_rec.CHECK_NO THEN NULL
WHEN bsa_rec.OVERRIDDEN_CHECK_NO != bsa_rec.CHECK_NO THEN LPAD(TRIM(bsa_rec.OVERRIDDEN_CHECK_NO), 12, '0')
END
WHEN (btn = '2') THEN '1740 - Previously Paid Warrant'
ELSE NULL
END),
OVERRIDDEN_AMOUNT = --(CASE :btn
(CASE WHEN (btn = '1') THEN CASE WHEN bsa_rec.OVERRIDDEN_AMOUNT = bsa_rec.AMOUNT THEN NULL
WHEN bsa_rec.OVERRIDDEN_AMOUNT != bsa_rec.AMOUNT THEN LPAD(TRIM(bsa_rec.OVERRIDDEN_AMOUNT), 12, '0')
END
WHEN (btn = '2') THEN NULL
ELSE NULL
END),
OVERRIDDEN_DATE = SYSDATE,
OVERRIDDEN_USER_ID = bsa_rec.OVERRIDDEN_USER_ID,
CHECK_NO = (CASE btn
WHEN '1' THEN LPAD(TRIM(bsa_rec.CHECK_NO), 12, '0')
WHEN '2' THEN LPAD(TRIM(bsa_rec.CHECK_NO), 12, '0')
ELSE NULL
END),
AMOUNT = (CASE btn
WHEN '1' THEN TRIM(bsa_rec.OVERRIDDEN_AMOUNT)
WHEN '2' THEN TRIM(bsa_rec.AMOUNT)
ELSE NULL
END)
WHERE TO_NUMBER(CHECK_NO) = (CASE btn
WHEN '1' THEN bsa_rec.OVERRIDDEN_CHECK_NO
WHEN '2' THEN bsa_rec.CHECK_NO
ELSE NULL
END)
AND AMOUNT = (CASE btn
WHEN '1' THEN bsa_rec.OVERRIDDEN_AMOUNT
WHEN '2' THEN bsa_rec.AMOUNT
ELSE NULL
END)
AND TRUNC(LOAD_DATE) = (CASE btn
WHEN '1' THEN TRUNC(bsa_rec.LOAD_DATE)
WHEN '2' THEN (SELECT MAX(LOAD_DATE) FROM WAREHOUSE.BANK_STATEMENT_ACTIVITY)
ELSE NULL
END)
AND BANKACCTNO = (SELECT LONGDESC
FROM TCMS.COMPLEMENTARY_VALIDATIONS
WHERE TEXTCODE = 'BANKACCT'
AND CODE = 80);
COMMIT;
END UpdateBankStatementActivity;
最初のSQLコードスニペットのパラメータ値は、PL/SQLブロック内のパラメータと一致しています。
私はこれがうまくいくと思います。アップデート前のデータ、アップデート実行(変数値を含む)、アップデート後のデータを掲載してください。私は働いていない単一の列が質問を説明するのに十分であると信じています。 – Aleksej
mathguyは私が訂正したロジックを指摘し、エディタを介して更新を行います。しかし、パッケージを介して実行すると、テーブルは更新されていません...できるだけ早くサンプルを提供します。 – TheSchnitz
@ TheSchnitz - パッケージ内のプロシージャのコードを変更して、すべてを再コンパイルしてください。それ以外の場合は、Oracleは引き続き「最後に正常終了」バージョンを使用します。 – mathguy