社内の質問箱に、APEXコレクションを対話グリッドで扱うには?という質問があったので、試しに実装してみました。
そもそもAPEXコレクションとは?
マニュアルのこちらに説明があります。開始されたセッションに紐づけて、データを保存や参照をすることができます。
データベースの一時表に似ていますが、Oracle APEXのそれぞれのリクエストは異なるデータベースのセッションで処理が行われるため、データベースのセッションに紐づけて行を保存する一時表は使えません。
APEX_COLLECTIONの初期化
セッションの開始後に、アプリケーション・プロセスなどでコレクションを作成します。以下の例ではコレクションの名前をTESTにしています。
apex_collection.create_or_truncate_collection( p_collection_name => 'TEST' );
対話グリッドの定義
ソースとして与えるSQLの例は以下になります。SEQ_IDを主キーとして扱うので、これは必ず含めます。それ以外はデータの保存に使用している列を含めます。以下の例ではC001とC002です。それ以外のカラムも必要にしたがって追加することができます。
select SEQ_ID, C001, C002 from APEX_COLLECTIONS where collection_name = 'TEST'属性の編集は有効にします。
主キーとなる列SEQ_IDの設定です。タイプを非表示とし、主キーをONにします。
プロセスの設定
対話グリッド上でデータが編集し保存を実行すると、変更分のみがサーバーへ送信されます。SQLのINSERT/UPDATE/DELETE文をAPEXコレクションに実行することはできないため、それに対応した処理をPL/SQLコードとして記述します。
ターゲット・タイプはPL/SQL Codeとし、行のロックはNoに設定します。コードには以下を記述します。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
begin | |
case :APEX$ROW_STATUS | |
when 'C' then | |
:SEQ_ID := apex_collection.add_member( | |
p_collection_name => 'TEST', | |
p_c001 => :C001, | |
p_c002 => :C002 | |
); | |
when 'U' then | |
apex_collection.update_member( | |
p_collection_name => 'TEST', | |
p_seq => :SEQ_ID, | |
p_c001 => :C001, | |
p_C002 => :C002 | |
); | |
when 'D' then | |
apex_collection.delete_member( | |
p_collection_name => 'TEST', | |
p_seq => :SEQ_ID | |
); | |
end case; | |
end; |
このように実装することで、APEXコレクションを対話グリッドで扱うことが可能になります。
今回作成したアプリケーションのエクスポートを以下に置きました。
https://github.com/ujnak/apexapps/blob/master/exports/collection-and-grid.zip
Oracle APEXのアプリケーション作成の参考になれば幸いです。
完