e-learning、オラクル研修、LMS(学習管理システム)のiStudy

e-learning、オラクル研修、LMS(学習管理システム)のiStudy

第111回「WEBアプリ作成(9)データ更新(UPDATE)(2/2)」

2014.11.20

前回は、指定された社員のデータを読み込むデータ更新用のフォーム画面を作成しました。しかし、そのフォームの送信先のデータ更新処理プロシージャを完成させていないので、今回でそれを完成させましょう。

そのプロシージャの名前は、EMP2_UPDATE_EXEという名前でしたね。

このプロシージャを作成するために、まずフォームから送信されるリクエストパラメータの名前を正しく確認しなければなりません。そのためにはソースコードを確認して入力項目のNAME属性を調べればよいのですが、もっとおすすめな方法があります。それは、以前(第108回)も少しお話しましたが、一時的に入力フォームの<FORM>タグのMETHOD属性を"GET"にして、実際に送信ボタンを押してみればよいのです。
そうすれば送信先プロシージャのURLの後ろにリクエストパラメータが付加されますので、ブラウザのURLをみれば確実に正しく確認できます。
例えば、本メルマガではまだ扱っていませんが、チェックボックス<input type="checkbox" name="名前" value="値"> などはチェックをしていないと、パラメータそのものが送信されないのですが、そういった様子もMETHOD="GET"のフォームであれば確認できます。ちなみに、そのように送信されたり、送信されなかったりするリクエストパラメータがあるときは、それを受け止めるプロシージャ側のパラメータ定義にデフォルト値を指定してください。そうすれば送信されないパラメータがあってもデフォルト値で処理できますのでエラーになりません。たとえ、そのデフォルト値がNULLであっても、とにかくデフォルト値を指定していないと、送信されなかった場合エラーになりますので、注意してください。

※参考 パラメータのデフォルト値の指定の例  'ABC'というデフォルト値をもつパラメータ P1
(例1)
PROCEDURE PROC1 ( P1 IN VARCHAR2 := 'ABC')
(例2)
PROCEDURE PROC1 ( P1 IN VARCHAR2 DEFAULT 'ABC')

今回はそのようなデフォルト値が必要なパラメータはありません。送られてくるパラメータ名は以下の通りです。

P_EMPNO      -- 社員番号
P_ENAME      -- 社員名
P_DEPTNO     -- 所属する部門の番号
P_HIREDATE   -- 入社日
P_NOTE       -- 備考

これらのパラメータを使って、指定された社員番号の社員の各項目を更新(UPDATE)します。

リクエストパラメータは常に文字型(VARCHAR2)です。

では早速以下のような例でコーディングしてみましたので、ご覧ください。

SQL> SHOW USER
ユーザーは"SCOTT"です。

  1  CREATE OR REPLACE PROCEDURE EMP2_UPDATE_EXE
  2  ( P_EMPNO     IN VARCHAR2,
  3    P_ENAME     IN VARCHAR2,
  4    P_DEPTNO    IN VARCHAR2,
  5    P_HIREDATE  IN VARCHAR2,
  6    P_NOTE      IN VARCHAR2)
  7  IS
  8    V_HIREDATE  DATE;
  9    V_SQLERRM   VARCHAR2(500);
 10  BEGIN
 11    -- 入社日をDATE型に変換
 12    V_HIREDATE := TO_DATE(P_HIREDATE,'YYMMDD');
 13    -- EMP2表をUPDATE
 14    UPDATE EMP2
 15    SET ENAME = P_ENAME,
 16        DEPTNO = TO_NUMBER(P_DEPTNO),
 17        HIREDATE = V_HIREDATE,
 18        NOTE     = P_NOTE
 19    WHERE EMPNO = TO_NUMBER(P_EMPNO);
 20    -- 1行更新されていれば、確定
 21    IF SQL%ROWCOUNT = 1 THEN
 22       COMMIT;
 23       HTP.P('正常に1件、更新されました');
 24    ELSE
 25       ROLLBACK;
 26       HTP.P('更新処理が異常です。処理を取り消しました');
 27    END IF;
 28    HTP.P('<BR><A HREF="emp2_update_form?p_empno=' ||P_EMPNO||'">更新画面に戻る</A>');
 29  EXCEPTION
 30    WHEN OTHERS THEN
 31        V_SQLERRM := SQLERRM;
 32        HTP.P(V_SQLERRM);
 33* END EMP2_UPDATE_EXE;
SQL> /

プロシージャが作成されました。

では解説します。

まず2-6行目が、フォームから送信されてくるリクエストパラメータですね。ご覧のようにデータ型はすべて、VARCHAR2型です。(サイズは指定しない)

そして、これらのパラメータのうち特にチェックを必要とするのが、入社日(P_HIREDATE)です。なぜかというと、入社日の日付書式はYYMMDDである想定なのですが、前画面の更新フォームで、この部分は手入力です。したがって、YYMMDDの書式で入力されていない可能性があります。したがって、チェックの意味もかねて、12行目でTO_DATE関数で、YYMMDDの日付書式でDATE型に変換し変数に格納しているわけです。
もし、日付書式に反すれば、エラーとなり、30-32行目のOTHERSハンドラでシステムエラーメッセージ(SQLERRM)が表示されます。

データ型変換が必要な項目に部門番号(P_DEPTNO)や、社員番号(P_EMPNO)もありますが、これらはいずれも前画面で手入力する項目ではありません。
たとえば部門番号(P_DEPTNO)は選択リストから選択しますし、社員番号は隠しパラメータ(<INPUT TYPE="HIDDEN" ・・・>) です。よって手入力ではないので、チェックの意味での事前のデータ型変換はせずに、UPDATE文の中で、直接TO_NUMBER関数で、データ型変換して使っています。
このあたりはプログラマーの考え方次第なので、こうしなければいけないというものではありません。

14行目からのUPDATE文は特に説明することはないと思います。指定された社員番号(P_EMPNO)の社員の各項目を更新しているわけです。

21行目で、処理行数(SQL%ROWCOUNT)をチェックし、1件であれば正常と判断し、COMMITし、正常である旨のメッセージを表示します。社員番号は主キーですから、必ず、1件の更新のはずです。

もし、1件でなければ、エラーと判断し、ROLLBACKしたうえで、異常である旨のメッセージを表示します。(24-26行目)

いずれにしろ、最後に「更新画面にもどる」という表示をします。(28行目)

ここで注目していただきたいのは、「更新画面に戻る」という文字にリンクを張っていることです。すなわち、アンカータグ(<A ・・>) です。このアンカータグのHREF属性がリンク先ですが、仮に、パラメータ P_EMPNOの値が、7938だとすると、以下のように生成されます。

<A HREF="emp2_update_form?p_empno=7938">更新画面に戻る</A>

ここで、「更新画面に戻る」という文字をクリックすると、今回の場合だとhttp://localost:8080/dad/emp2_update_form?p_empno=7938 というURLでリクエストが行われます。
よって社員番号7938の更新画面が再び表示される訳です。なお、HREF属性の記述はDAD(dad)よりも下(右側)の記述であることにも注目してください。もちろんURL全体(http://~)を記述することもできますが、同じDAD(DATA ACCESS DESCRIPTOR)内の処理であれば、DADの下の記述だけで結構です。

では早速、実行してみましょう。

前回の更新フォームを開きます。(ログインを求められたら、socttユーザとパスワードを指定してください)
http://localost:8080/dad/emp2_update_form?p_empno=7938

そして送信ボタンを押すと、emp2_update_exeに送信され、無事、1件の更新ができました。

そして、「更新画面に戻る」リンクをクリックすると、再び、更新フォーム画面が開いたわけです。
データベースから再びデータを読み込んだわけですが、ご覧のようにきちんと更新が反映されています。

いかがですか? 簡単ですね。この「WEBアプリを作成する」シリーズを読んでいる方はこれでだいたいのパターンがわかったと思います。もうたいていの業務的なアプリは作れそうですね。

では次回からは、すこし細かい点を話題に、トピックスを解説したいと思います。ご期待ください。

先頭へ戻る