OPEN ステートメント
OPEN ステートメントは、カーソルをオープンして、 そのカーソルを結果表からの行の取り出しに使用できるようにします。
呼び出し
対話式 SQL 機能には外見上対話式の実行に見えるインターフェースが用意されている場合がありますが、 このステートメントはアプリケーション・プログラムに組み込むことだけが可能です。 これは、動的に作成できない実行可能ステートメントです。 コマンド行プロセッサーを使用して呼び出した場合は、一部のオプションを指定できません。
詳しくは、 コマンド行 SQL ステートメントおよび XQuery ステートメントの使用 を参照してください。
許可
- モジュールで定義されていないグローバル変数に対する READ 特権
- モジュールで定義されているグローバル変数のモジュールに対する EXECUTE 特権
- モジュールで定義されているグローバル変数のモジュールが含まれているスキーマに対する EXECUTEIN 特権
- モジュールで定義されているグローバル変数のモジュールが含まれているスキーマに対する DATAACCESS 権限
このステートメントは動的に準備できないので、グループ特権は考慮されません。
構文
説明
- cursor-name
- プログラムのそれ以前の個所にある DECLARE CURSOR ステートメントで定義されているカーソルの名前を指定します。 cursor-name が SQL プロシージャー内の WITH RETURN TO CLIENT と宣言されているカーソルを指定したときに、そのカーソルが既にオープン状態だった場合、既存のオープン・カーソルは結果セット・カーソルになって cursor-name を使用してアクセスすることができなくなり、新しいカーソルがオープンして cursor-name を使用してアクセスできるようになります。 これ以外の場合は、この OPEN ステートメントが実行される時点で、cursor-name で指定されたカーソルはクローズ状態でなければなりません。DECLARE CURSOR ステートメントは、次のいずれかの方法で、 SELECT ステートメントを指定しなければなりません。
- その DECLARE CURSOR ステートメントに SELECT ステートメントを組み込む。
- 準備済み SELECT ステートメントを指定する statement-name を組み込む。
カーソルの結果表は、その SELECT ステートメントを評価することによって得られます。 評価の際には、その SELECT ステートメントで指定されている特殊レジスター、グローバル変数、または PREVIOUS VALUE 式の現行値と、SELECT ステートメントまたは OPEN ステートメントの USING 節で指定されたホスト変数の現行値が使用されます。 結果表の行は、OPEN ステートメントの実行中に得られ、それらを入れる一時表が作成されるか、あるいは後続の FETCH ステートメントの実行中に得られます。 いずれの場合でも、カーソルはオープン状態になり、その位置はその結果表の最初の行の前になります。 表が空の場合、カーソルの状態は事実上 「
最後の行の後
」になります。 カーソル変数名 (cursor-variable-name) カーソル変数の名前を指定します。 カーソル変数の値は、NULL であってはなりません (SQLSTATE 34000)。 カーソルの値コンストラクターが直接または間接的に割り当てられたカーソル変数は、その割り当てと同じ有効範囲にある OPEN ステートメントでのみ使用できます (SQLSTATE 51044)。 カーソル変数に割り当てられたカーソルの値コンストラクターで、statement-name を指定した場合、OPEN ステートメントは、その statement-name が明示的または暗黙的に宣言された有効範囲と同じ有効範囲内にある必要があります (SQLSTATE 51044)。
この OPEN ステートメントが実行される時点で、カーソル変数の基礎となるカーソルはクローズ状態でなければなりません。 基礎となるカーソルの結果表は、その SELECT ステートメントまたはカーソル変数に関連付けられた動的ステートメントを評価することによって得られます。 評価の際には、その SELECT ステートメントで指定されている特殊レジスター、グローバル変数、または PREVIOUS VALUE 式の現行値と、SELECT ステートメントまたは OPEN ステートメントの USING 節で指定された変数の現行値が使用されます。 結果表の行は、OPEN ステートメントの実行中に得られ、それらを入れる一時表が作成されるか、あるいは後続の FETCH ステートメントの実行中に得られます。 いずれの場合でも、カーソルはオープン状態になり、その位置はその結果表の最初の行の前になります。 表が空の場合、カーソルの状態は事実上 「
最後の行の後
」になります。cursor-variable-name を使用する OPEN ステートメントは、コンパウンド SQL (コンパイル済み) ステートメント内でのみ使用できます。
expression, )- パラメーター化されたカーソル変数の名前付きパラメーターに関連付けられている引数を指定します。 カーソル変数に割り当てられた cursor-value-constructor は、指定された引数の数と同数のパラメーターを持つパラメーターのリストが含まれている必要があります (SQLSTATE 07006 または 07004)。 n 番目の式のデータ・タイプと値は、n 番目のパラメーターに割り当て可能でなければなりません (SQLSTATE 07006 または 22018)。 使用する
この後に、カーソルのステートメント内のパラメーター・マーカーまたは変数に代入する値を指定します。 パラメーター・マーカーの説明については、『
PREPARE
』を参照してください。statement-name を DECLARE CURSOR ステートメント、またはパラメーター・マーカーを含むカーソル変数に関連付けられたカーソルの値コンストラクターで指定した場合、USING の使用が必須です。 準備済みステートメントにパラメーター・マーカーが含まれていない場合、USING は無視されます。
select-statement を DECLARE CURSOR ステートメント、またはカーソル変数に関連付けられた非パラメーター化カーソルの値コンストラクターで指定した場合、USING を変数値のオーバーライドに使用できます。
variable変数とホスト変数の宣言規則に従って、該当プログラムで宣言されている変数またはホスト構造体を指定します。 変数の数は、準備済みステートメントのパラメーター・マーカーの数と同じでなければなりません。 n 番目の変数は、 準備済みステートメントの n 番目のパラメーター・マーカーに対応します。 場合によっては、ロケーター変数とファイル参照変数も、パラメーター・マーカーの値のソースとして指定できます。
expression- 式を使用してパラメーター・マーカーに関連付ける値を指定します。 式を USING 節に指定する OPEN ステートメントは、コンパウンド SQL (コンパイル済み) ステートメント内でのみ使用できます (SQLSTATE 42601)。 式の数は、準備済みステートメントのパラメーター・マーカーの数と同じでなければなりません (SQLSTATE 07001)。 n 番目の式は、準備済みステートメントの n 番目のパラメーター・マーカーに対応します。 n 番目の式のデータ・タイプと値は、n 番目のパラメーター・マーカーに関連付けられたタイプに割り当て可能でなければなりません (SQLSTATE 07006)。
ルール
- カーソルの SELECT ステートメントが評価される場合に、 そのステートメント中の各パラメーター・マーカーは、対応するホスト変数によって置き換えられます。 型付きパラメーター・マーカーの場合、ターゲット変数の属性は CAST 指定によって指定されます。 タイプなしパラメーター・マーカーの場合、 ターゲット変数の属性はパラメーター・マーカーのコンテキストに従って決定されます。
- V は、パラメーター・マーカー P に対応するホスト変数を表します。 V の値は、列への値の割り振り規則に従って、P のターゲット変数に割り当てられます。 したがって、
- V はターゲットと互換でなければなりません。
- V がストリングの場合、その長さ (ただし、 LONG ストリングでないストリングの末尾ブランクは含まない) はターゲットの長さ属性を超えることはできません。
- V が数値の場合、 V の整数部分の絶対値はターゲットの整数部分の絶対値の最大を超えることはできません。
- V の属性がターゲットの属性と同一でない場合、 その値はターゲットの属性に合うように変換されます。
カーソルの SELECT ステートメントが評価されるとき、P の代わりに使用される値は P のターゲット変数の値になります。 例えば、V が CHAR(6) でターゲットが CHAR(8) の場合、P の代わりに使用される値は V の値にブランクを 2 個付加したものになります。
- USING 節は、パラメーター・マーカーを含む準備済み SELECT ステートメントのために用意されています。 ただし、これは、カーソルの SELECT ステートメントが DECLARE CURSOR ステートメント、またはカーソル変数に関連付けられた非パラメーター化カーソルの値コンストラクターの一部である場合にも使用できます。 このような場合、OPEN ステートメントは、 あたかも SELECT ステートメントの各ホスト変数がパラメーター・マーカーであるかのように実行されます。 ただし、ターゲット変数の属性は SELECT ステートメントのホスト変数と同じになります。 その結果、USING 節に指定するホスト変数の値によって、 カーソルの SELECT ステートメントの中のホスト変数の値がオーバーライドされることになります。 変数値のオーバーライドは、SELECT ステートメントでは他の変数をなにも組み込まないため、パラメーター化されたカーソル変数をオープンする際には使用しないでください。
- カーソル定義に組み込まれている SQL データを変更する SQL データ変更ステートメントとルーチンは完全に実行され、
結果セットは、カーソルのオープン時に一時表に保管されます。 ステートメントの実行が正常に完了すると、SQLERRD(3) フィールドには、挿入、更新、
および削除操作が可能な行の数の合計が入ります。 全選択内にデータ変更ステートメントを含むカーソルが関係する OPEN ステートメントの実行中にエラーが発生した場合は、
そのデータ変更ステートメントがロールバックされます。
OPEN ステートメントの明示的なロールバック、 つまり OPEN ステートメント以前のセーブポイントまでのロールバックにより、カーソルはクローズします。 カーソルの定義で、全選択の FROM 節内にデータ変更ステートメントが含まれている場合、 データ変更ステートメントの結果はロールバックされます。
SELECT ステートメントや SELECT INTO ステートメントにネストされていたデータ変更ステートメントで、 ターゲット表の行に対して行われた変更は、カーソルがオープンされるときに処理されるため、 カーソルに対するフェッチ操作の途中でエラーが発生しても、変更が元に戻ることはありません。
注
- クローズ状態のカーソル: プログラムが開始された時点、
およびプログラムが ROLLBACK ステートメントを開始した時点では、
そのプログラム中のすべてのカーソルはクローズ状態になります。
WITH HOLD として宣言されたオープン・カーソル以外のすべてのカーソルは、 プログラムが COMMIT ステートメントを発行する際にクローズ状態になります。
また、 CLOSE ステートメントを実行した場合、 またはカーソル位置が予期できなくなるようなエラーが検出された場合にも、カーソルはクローズ状態になることがあります。
カーソル変数の基礎となるカーソルは、そのカーソル変数が有効範囲外になり、その基礎となるカーソルを参照したカーソル変数が他に存在しない場合はクローズされます。
- カーソルの結果表から行を取り出すには、 カーソルがオープンされている時に FETCH ステートメントを実行します。 カーソルの状態をクローズからオープンに変更する唯一の方法は、 OPEN ステートメントを実行することです。
- マテリアライズ結果表の効果: カーソルが読み取り専用でない時など、場合によっては、FETCH ステートメントの実行の過程でカーソルの結果行が得られる場合があります。 また、代わりに、マテリアライズ結果表メソッドが使用される場合もあります。 マテリアライズ結果表メソッドでは、結果表全体が OPEN ステートメントの実行中に一時バッファーに転送されます。 一時バッファーが使用される場合、プログラムの結果は、以下の点で異なる可能性があります。
- 以後の FETCH ステートメントまでは起こることのないエラーが、 OPEN の過程で起こる可能性があります。
- カーソルがオープン状態の間、同じトランザクションで実行された INSERT、 UPDATE、 および DELETE ステートメントは結果表に影響を与えません。
- OPEN の実行中に、結果表の行ごとに SELECT ステートメント中の NEXT VALUE 式が評価されます。
逆に、一時バッファーを使用しない場合、カーソルがオープン状態の間に実行される INSERT、 UPDATE、および DELETE ステートメントが、 同じ作業単位から発行される場合には結果表に影響を与えることがあり、 個々の行が取り出されるたびに SELECT ステートメント中の NEXT VALUE 式が評価されます。 この結果表は、同じ作業単位で実行される操作による影響を受けることがあり、 そのような操作の影響は、必ずしも予測可能であるとは限りません。 例えば、カーソル C の位置が SELECT * FROM T と定義された結果表の 1 つの行である場合に、 T に新しい行を挿入すると、行の順序が整っていないために、 その挿入が結果表に与える影響は予測できません。 したがって、後続する FETCH C で T の新しい行が取り出される場合もあれば、取り出されない場合もあります。
- ステートメントのキャッシュは、 OPEN ステートメントによってオープンと宣言されているカーソルに影響を与えます。
- 同一カーソルの複数回オープン: SQL プロシージャー内の WITH RETURN TO CLIENT と宣言されたカーソルは、同じ名前のカーソルが既にオープン状態のときでもオープンできます。 この場合、既存のオープン・カーソルは結果セット・カーソルになり、カーソル名でアクセスできなくなります。 新しいカーソルがオープンし、カーソル名でアクセス可能になります。 新しいカーソルをクローズしても、以前に名前でアクセスできたカーソルは、再度カーソル名でアクセス可能にはなりません。 この方法で結果セット・カーソルになるカーソルは、サーバーではアクセスできず、クライアントのみで処理できます。
- 非ブロック・カーソルを使用する SQL プロシージャーまたは外部ストアード・プロシージャーが WITH RETURN カーソルを開いても、1 行もフェッチしない場合は、カーソル照会のアクセス・プランが評価されないことがあります。 照会の評価は、呼び出し元またはクライアントがプロシージャーの結果セットから行をフェッチするときに行われます。
例
- カーソル C1 を定義します。このカーソルは、DEPARTMENT 表から管理部門 (ADMRDEPT) 'A00' によって管理される部門の行すべてを検索するために使用します。
- 最初に取り出す行の前に、カーソル C1 を置きます。
EXEC SQL DECLARE C1 CURSOR FOR SELECT DEPTNO, DEPTNAME, MGRNO FROM DEPARTMENT WHERE ADMRDEPT = 'A00' END-EXEC. EXEC SQL OPEN C1 END-EXEC.
EXEC SQL BEGIN DECLARE SECTION;
static short hv_int;
char hv_vchar64[65];
char stmt1_str[200];
EXEC SQL END DECLARE SECTION;
EXEC SQL PREPARE STMT1_NAME FROM :stmt1_str;
EXEC SQL DECLARE DYN_CURSOR CURSOR FOR STMT1_NAME;
EXEC SQL OPEN DYN_CURSOR USING :hv_int, :hv_vchar64;
EXEC SQL BEGIN DECLARE SECTION;
char stmt1_str[200];
EXEC SQL END DECLARE SECTION;
EXEC SQL INCLUDE SQLDA;
EXEC SQL PREPARE STMT1_NAME FROM :stmt1_str;
EXEC SQL DECLARE DYN_CURSOR CURSOR FOR STMT1_NAME;
EXEC SQL OPEN DYN_CURSOR USING DESCRIPTOR :sqlda;
- カーソルを出力カーソル変数に割り当てます。
- カーソルをオープンします。
CREATE PROCEDURE PROC1 (OUT P1 CURSOR)LANGUAGE SQL
BEGIN
SET P1=CURSOR FOR SELECT DEPTNO, DEPTNAME, MGRNO FROM DEPARTMENT WHERE ADMRDEPT='A00'; --
OPEN P1; --
END;