Example - Cursor variables

Top  Previous  Next

Version 7.2以来、Oracleはカーソル変数をサポートしています。この変数は、サーバー上で定義されオープンされたselect命令のためのカーソルへの参照です。次のような利点があります:

w        カーソルはサーバー上のセントラルポイントで定義され維持されます
w        エンドユーザーはカーソルの内部オブジェクト上ではなく、プロシージャー上の特権を実行する必要があります

TOracleQueryとしてカーソル変数を使う

カーソル変数はselect命令付きTOracleQueryに相当するものなので、 DOAToracleQueryとしてカーソル変数型を実装します。カーソル変数を使うために、少なくとも2つのTOracleQueryコンポーネントが必要です: 一つはカーソルをオープンするプロシージャーを呼ぶためのPL/SQLブロック

ともう一つはカーソル自身のためです:

begin

with Query1 do

begin

   Clear;

   SQL.Add('begin');

   SQL.Add('  employee.opencursor(:p_empcursor, :p_order)');

   SQL.Add('end;');

   DeclareVariable('p_empcursor', otCursor);

   DeclareVariable('p_order', otString);

   SetComplexVariable('p_empcursor', CursorQuery);

   SetVariable('p_order', 'ename');

   Execute;

end;

with CursorQuery do

begin

   Execute;

   while not Eof do

   begin

     Memo.Items.Add(Field('ename'));

     Next;

   end;

end;

end;

 

パッケージ化されたプロシージャーemployee.opencursorはこのようになるかもしれません:

type t_empcursor is ref cursor return emp%rowtype;

 

procedure getcursor(p_empcursor in out t_empcursor, p_order in varchar2) is

begin

if p_order = 'ename' then

   open p_empcursor for select * from emp order by ename;

elsif p_order = 'empno'

   open p_empcursor for select * from emp order by empno;

else

   open p_empcursor for select * from emp;

end if;

end;

 

このサンプルでは、Query1は一定の順序で全てのemployeeを選択するためにカーソルをオープンするのにパッケージ化されたemployee.opencursor関数を呼び出します。CursorQueryp_empcursor 変数に割り当てられます。このためにはSetComplexVariableメソッドを使ってください。次に、全ての列はフェッチされ、employeeの名前はメモ内に表示されます。

TOracleDataSet内のカーソル変数を使う

カーソル変数に基づきTOracleDatasetを作成するために、SQLプロパティ内にカーソルをオープンするプロシージャーへの呼び出しと共にPL/SQLブロックを入力します。例えば:

begin

employee.opencursor(:p_empcursor, :p_order);

end;

 

もし:p_empcursor変数をotCursorとして宣言したら、データセットはカーソルを検出し、データセットがオープンさリフレッシュされる時PL/SQLブロックが実行されたあとにカーソルからレコードを取得します。

データセット内のカーソル変数の結果を更新可能にするためには、カーソルにrowidをいれてください、ちょうど通常のデータセットのselect命令つきのもののように。こうするためには、次のように、パッケージ内にカーソルの型とプロシージャーを定義してください:

cursor empcursor is select emp.*, rowid from emp;

type t_empcursor is ref cursor return empcursor%rowtype;

procedure opencursor(p_empcusor in out t_empcursor, p_order in varchar2);

 

rowidが含まれたら、データセットはそれを使ってレコードをlock, refresh, updateもしくはdeleteすることが出来ます。データセットのUpdatingTableプロパティ内の更新テーブルを指定する必要もあります。 この場合: empとなります。 通常データセットはSQLプロパティ内のselect命令を調べることによって、更新テーブルを決定します。 しかしカーソル変数の場合これは不可視です。