DirectoOracleAccessを使ってストアドプロシージャを呼び出します。
プロシージャ呼出の基本3パターン
以下の3つについて順に説明します。
- 結果を返さないプロシージャの呼び出し(INPUT変数の渡し方)
- プロシージャ呼出し後、OUTPUT変数からの結果の取得
- カーソル変数を利用したプロシージャからのレコードセットの取得
1)結果を返さない手続き型のプロシージャ
|
右のようなプロシージャを考えます(引数を10回くりかえしてDBMS_Output出力します) |
create or replace procedure TestProc1(N IN NUMBER) is
i number;
begin
for i in 1 .. 10 loop
dbms_output.put_line(N);
end loop;
end TestProc1;
|
|
これを右のようなアプリケーションで呼んでみましょう 画面上のオブジェクトは左上から順に Session: TOracleSession Query1: TOracleQuery Button1: TButton Memo: TMemo で、 SessionのユーザID/Passwd/Database が適切に設定されてDBに接続でき Query1.SessionがSessionになっているとします |
![]() |
|
1-1(引数なしのとき) Query1.SQLをこのように設定して |
begin TestProc1( 3 ); end; |
|
Button1.Clickイベントをこう記述して
|
procedure TForm1.Button1Click(Sender: TObject); var Status: integer; Line: string; begin Session.DBMS_Output.Enable(100000); Query1.Execute; |
|
テスト実行すると結果は
|
メモに数字の3が10回繰り返して表示されるはずです。 |
|
TestProc1の引数を変数から与えるには Query1.SQLをこのように設定して |
begin TestProc1( :N ); end; |
|
Query1のVariablesプロパティのプロパティエディタを開いて、「Scan SQL」を実行すると、上記SQL文中からパラメータが抽出されてVariablesとしてリストに現れます。 一番目の「:N」をクリックして、 整数型として定義します。 |
![]() |
|
フォーム上にエディットボックスEdit1を置いて、 今度はButton1.Clickをこのように変えて |
procedure TForm1.Button1Click(Sender: TObject);
var
Status: integer;
Line: string;
begin
Session.DBMS_Output.Enable(100000);
with Query1 do begin
Close;
SetVariable(★
|
| 実行し、Edit1に数字をいれてボタンをクリックすると、結果は… | Edit1に入力した数字が10回繰り返されて出力されます |
2)計算結果をパラメータで返すストアドプロシージャ
|
例としてインプットを二乗して返す手続きを用意した |
create or replace procedure TestProc2( N IN NUMBER, R OUT NUMBER) is begin R := N * N; end TestProc2; |
|
Query1.SQLを右のようにセット
|
declare R number; begin TestProc2(6, R); select R into :R From Dual; end; |
| Query1.Variablesプロパティのプロパティエディタを開き、出力パラメータ:Rを設定する | ![]() |
| Button1Clickは右のようにして |
procedure TForm1.Button1Click(Sender: TObject); begin Query1.Execute; Memo.Clear; Memo.Lines.Add(★
|
|
実行すれば
|
メモに「 R = 36 」と出力される |
|
補足
|
上記の例においては、Query1.SQLを以下のようにした方がもっと直接的です。 begin TestProc2( 6, :R); end; または begin TestProc2( N => 6, R => :R); end; なお、プロシージャをパッケージ内で宣言した場合は、TOraclePackageコンポーネントが簡便です。 |
3)SELECT文の結果を返すストアドプロシージャ
|
右のようなパッケージを用意します
Sybase/SQL-Server風にいえば create procedure SelectRecords as begin select empno, ename from emp; end; のような感じにしたい場合の話です。 |
create or replace package TestPkg is cursor empcursor is select empno, ename from emp; type t_empcursor is ref cursor return empcursor%rowtype; procedure SelectRecords(p_empcursor in out t_empcursor); end TestPkg; create or replace package body TestPkg is
procedure SelectRecords(p_empcursor in out t_empcursor) is
begin
open p_empcursor for select empno, ename from emp;
end;
end TestPkg;
|
|
では、このプロシージャSelectRecordsの結果セットをグリッド表示してみましょう。 先程までのテストプログラムのTQueryの代わりにTOracleDataSetを使い、MemoのかわりにDBGridを配置して右のような画面を作ります。 |
![]() |
| OracleDataSet1.SQLは次のようにセットします |
begin TestPkg.SelectRecords( :CURSOR ); end; |
|
※重要!トリッキーですが…※ OracleDataSet1.Variablesのプロパティエディタで Cursor型のVariableとしてCURSORを定義します こうすると、この変数が、当データセットのためのカーソルになるのです。 |
![]() |
|
Button1Clickイベントで、OracleDataset1を開くように設定しておく
|
procedure TForm1.Button1Click(Sender: TObject); begin OracleDataSet1.Open; end; |
|
これを実行すると、プロシージャが実行され、出力用のカーソルの指すデータセットがグリッド表示されます。 そうです。Oracleのストアドプロシージャでselect文を実行させた、その結果をデータベース対応コンポーネントで参照・編集が可能です。 |
![]() |
|
補足
|
カーソルの定義に、ROWIDを取得対象に含めることで、更新可能なデータセットになります。(DOAによるデータベース更新に関するトピックを参照のこと) |





