SQLExecDirect() - ステートメントを直接実行する

SQLExecDirect() は 、SQL ステートメントを 1 ステップで準備し、実行します。

SQLExecDirect() は、いずれかのパラメーターがステートメントにある場合、パラメーター・マーカー変数の現行値を使用します。 ステートメントは一度のみ実行できます。

SQLExecDirect() の ODBC 仕様

表 1. SQLExecDirect() 仕様
ODBC 仕様レベル X/Open CLI CAE 仕様 ISO CLI 仕様
1.0 はい はい

構文

SQLRETURN   SQLExecDirect    (SQLHSTMT          hstmt,
                              SQLCHAR     FAR   *szSqlStr,
                              SQLINTEGER        cbSqlStr);

関数引数

次の表は、この関数のそれぞれの引数ごとに、 データ・タイプ、用途、および説明を示しています。

表 2. SQLExecDirect() 引数
データ・タイプ 引数 使用 説明
SQLHSTMT hstmt input SQL ステートメントを実行するステートメント・ハンドルを指定します。 この引数で使用するステートメント・ハンドルでは、オープン・カーソルを関連付ける ことはできません。 ステートメント・ハンドルを解放またはリセットする方法については、SQLFreeStmt() を参照してください。
SQLCHAR * szSqlStr input SQL ステートメントを含むストリングを指定します。 接続されたデータベース・サーバーは、ステートメントを準備できる必要があります。
SQLINTEGER cbSqlStr input 引数 szSqlStr の内容の長さ (バイト) を指定します。 この長さは、ステートメントの正確な長さに設定するか、あるい はステートメントが NUL 終了である場合は SQL_NTS に設定する必要があります。

使用法

SQL ステートメントを 2 回以上実行する予定の場合、あるいは照会実行前に 結果セットの列に関する情報を取得する必要がある場合は、SQLExecDirect() の代わりに SQLPrepare() および SQLExecute() を使用してください。

SQLExecDirect() を使用するには、接続されたデータベース・サーバーが、 ステートメントを動的に作成できる必要があります。

SQL ステートメント・テキストにベンダー・エスケープ文節シーケンスが含まれる場合、Db2 ODBC は、準備および実行用に送信する前に、まず SQL ステートメント・テキストを適切な Db2 固有のフォーマットに変更します。 ベンダー・エスケープ文節シーケンスを含んでいる SQL ステートメントをアプリケーションが 生成しない場合、 接続レベルで SQL_ATTR_NOSCAN ステートメント属性を SQL_NOSCAN_ON に設定します。 この属性を SQL_NOSCAN_ON に設定すると、ステートメントのスキャンが原因によるパフォーマンス の影響が回避されます。

この SQL ステートメントを COMMIT または ROLLBACK することはできません。 その代わりに、SQLEndTran() を呼び出して、COMMIT または ROLLBACK ステートメント を出す必要があります。

SQL ステートメント・ストリングには、パラメーター・マーカーを含めることができます。 パラメーター・マーカーは疑問符 (?) で表されます。これは、SQLExecDirect() が呼び出される際に、アプリケーション提供の値が置き換えられるステートメント上に位置を示すために使用されます。 パラメーター・マーカーの値は、以下のソースから取得することができます。
  • アプリケーション変数。

    SQLBindParameter() は、アプリケーション・ストレージ域をパラメーター・マーカーにバインドするために使用されます。

  • LOB ロケーターが参照するサーバーにある LOB 値。

    SQLBindParameter() を使用して、LOB ロケーターをパラメーター・マーカーにバインド します。 LOB の実際の値はサーバーに保持されます。この値は、 別の SQL ステートメントの入力パラメーター値として使用されるまで、 アプリケーションに転送する必要はありません。

SQLExecDirect() を呼び出す前に、すべてのパラメーターをバインドする必要があります。

SQL ステートメントが照会の場合、SQLExecDirect() はカーソル名を生成し、 カーソルをオープンします。 アプリケーションが SQLSetCursorName() を使用してカーソル名をステートメントハンドルに関連付けている場合、 Db2 ODBC はアプリケーションが生成したカーソル名を内部で生成されたカーソル名に関連付けます。

結果セットが生成されると、SQLFetch() または SQLExtendedFetch() は、 データの次の行 (1 行または複数行) を取り出して、バインドされた変数の中に入れます。 また、バインドされなかった列についても、SQLGetData() を呼び出すことにより、 データを取り出すことができます。

SQL ステートメントが位置付け DELETE または位置付け UPDATE の場合、 そのステートメントで参照されたカーソルを行に位置付け、 同じ接続ハンドルの個別のステートメント・ハンドル で定義する必要があります。

SQL ステートメントをステートメント・ハンドルで 実行する前に、オープン・カーソルがそのステートメントにあってはなりません。

SQLSetStmtAttr() に電話して、入力パラメータ値の配列が各パラメータマーカーにバインドされていることを指定する場合は、入力パラメータ値の配列全体を処理するために SQLExecDirect() に電話する必要があるのは1回だけです。

FOR n ROWS 文節は、SQLExecDirect() を用いて実行する MERGE ステートメントで指定できません。 SQLSetStmtAttr() とSQL_ATTR_PARAMSET_SIZEステートメント属性を使用して、マージする行数を指定します。

戻りコード

SQLExecDirect() は、呼び出された後、次のいずれかの値を戻します。
  • SQL_SUCCESS
  • SQL_SUCCESS_WITH_INFO
  • SQL_ERROR
  • SQL_INVALID_HANDLE
  • SQL_NEED_DATA
  • SQL_NO_DATA_FOUND

アプリケーションが実行時データ・パラメーター値を要求すると、SQL_NEED_DATA が戻され ます。 SQLParamData() および SQLPutData() を呼び出して、これらのデータ・パラメーター値を SQLExecDirect() に提供します。

SQL ステートメントが検索 UPDATE または検索 DELETE であり、 検索条件を満たしている行がない場合、SQL_SUCCESS が戻されます。 SQLRowCount() を使用して、表あるいは表のビューに対して実行された UPDATE、INSERT、 または DELETE ステートメントの影響を受けた表の行数を判別します。

診断

次の表は、この関数が生成する各 SQLSTATE 値ごとに、 その記述と説明を一覧で記載してあります。

表 3. SQLExecDirect() SQLSTATE
SQLSTATE 説明 説明
01 5 04 UPDATE または DELETE ステートメントに、WHERE 節がありません。 引数 szSqlStr に UPDATE または DELETE ステートメント が含まれていますが、WHERE 文節がありません。 (表に行がない場合、 関数は SQL_SUCCESS_WITH_INFO または SQL_NO_DATA_FOUND を戻します。)
0700 1 パラメーターの数が正しくありません。 SQLBindParameter() を用いてアプリケーション変数にバインドされたパラメーターの数が、 引数 szSqlStr に含まれている SQL ステートメントのパラメーター・マーカーの 数より小さくなっています。
07006 無効な変換です。 Db2 ODBC とアプリケーション変数の間でデータを転送すると、互換性のないデータ変換が行われます。
08S01 通信リンク障害が発生しました。 関数が完了する前に、アプリケーションとデータ・ソース間の 通信リンクで障害が発生しました。
21S01 挿入値リストが列リストに一致していません。 引数 szSqlStr には INSERT ステートメントが含まれており、 挿入される値の数が派生表の程度と一致しませんでした。
21S02 派生表の次数が列リストに一致していません。 引数 szSqlStr には CREATE VIEW ステートメントが含まれており、 指定された名前の数が照会指定で定義された派生表と同じ程度ではありません。
2 20 01 ストリング・データの右側が切り捨てられました。 文字タイプの列に割り当てられた文字ストリングが、列の最大長を超えました。
22008 無効な日付時刻形式または日付時刻フィールドがオーバーフローです。 次の 1 つ以上の理由に該当した場合に、この SQLSTATE が戻されます。
  • 引数 szSqlStr は、無効な日時形式を指定した SQL ステートメントを含んでいます。 (すなわち、無効なストリング表記または無効な値が指定されたか、あるいは値が無効な日付です。)
  • 日時フィールドでオーバーフローが起こりました。

    例: 日付またはタイム・スタンプの算術計算の結果が日付の有効範囲から外れているか、 あるいは、バインドされた変数が小さすぎて日付/時刻値を割り当てることができません。

22012 ゼロによる除算は無効です。 引数 szSqlStr は算術式を伴う SQL ステートメントを持っていますが、 それが除数ゼロで割り算を行いました。
22018 割り当てにエラーがありました。 次の 1 つ以上の理由に該当した場合に、この SQLSTATE が戻されます。
  • 引数 szSqlStr には、パラメーターまたはリテラルが指定された SQL ステートメントが入っています。値または LOB ロケーターは、 関連する表列のデータ・タイプとは互換性がありません。
  • パラメータ値に関連付けられた長さ( pcbValue バッファの内容は、 SQLBindParameter() 関数)は無効です。
  • その fSqlTypeSQLBindParameter() で使用されている引数は、SQLグラフィックデータ型を表しますが、遅延長引数( pcbValue )には、奇妙な長さの値が含まれています。 GRAPHIC データ・タイプの場合、長さの値は偶数でなければなりません。
23000 保全性制約違反です。 この SQL ステートメントの実行は許可されていません。その理由は、データベース管理システムにおける整合性を保つための制約に違反する恐れがあるためです。
24000 カーソルの状態が無効です。 ステートメント・ハンドルでカーソルがオープン状態です。
2450 4 UPDATE、DELETE、SET、または GET ステートメントで識別されたカーソルが、行に位置付けられていません。 直前の照会からのステートメント・ハンドル上で、結果がペンディングになっているか、 あるいは、ステートメント・ハンドルに関連したカーソルがその時点ではまだクローズされていませんでした。
34000 カーソル名が無効です。 引数 szSqlStr に位置付け DELETE または位置付け UPDATE が含まれていますが、 ステートメントが参照するカーソルがオープン状態ではありません。
37 xxx 1 SQL 構文が無効です。 引数 szSqlStr には、以下の 1 つ以上のステートメント・タイプが含まれています。
  • COMMIT
  • ROLLBACK
  • 接続されたデータベース・サーバーが準備できない SQL ステートメント
  • 構文エラーのあるステートメント
4000 1 トランザクション・ロールバック。 SQL ステートメントが属しているトランザクションが、デッドロックまたはタイムアウト のためにロールバックされました。
42 xxx 1 構文エラーまたはアクセス規則違反。 これらの SQLSTATE は、以下のエラーのいずれかを示しています。
  • 425xx の場合、この許可 ID には、引数 szSqlStr に 含まれる SQL ステートメントを実行するための権限がありません。
  • 42xxx の場合は、ステートメントに関してさまざまな構文上の問題 またはアクセス上の問題があることを示しています。
4 28 95 EXECUTE または OPEN ステートメントのホスト変数の値は、データ・タイプが原因で使用できません。 次の 1 つ以上の理由に該当した場合に、この SQLSTATE が戻されます。
  • パラメーター・バインド関数呼び出しで指定された LOB ロケーター・タイプが、 パラメーター・マーカーの LOB データ・タイプと一致しません。
  • パラメーター・バインド関数で使用される引数 fSqlType は 、LOB ロケーター・タイプを指定しましたが、対応するパラメーター・マーカーは LOB ではありません。
42S01 データベース・オブジェクトは、既に存在しています。 引数 szSqlStr に、CREATE TABLE または CREATE VIEW ステートメントが 含まれていますが、指定された表名またはビュー名は既に存在しています。
42S02 データベース・オブジェクトは存在しません。 存在しない表名またはビュー名を参照する SQL ステートメントが、 引数 szSqlStr に含まれています。
42S11 索引は既に存在しています。 引数 szSqlStr に CREATE INDEX ステートメント が含まれていますが、指定された索引名は既に存在しています。
42S12 索引が見つかりません。 引数 szSqlStr に DROP INDEX ステートメントが含まれていますが、 指定された索引名が存在しません。
42S21 列はすでにあります。 引数 szSqlStr に ALTER TABLE ステートメントが含まれてい ますが、ADD 文節に指定された列は、固有でないか、または基本表の既存の列を示しています。
42S22 列が見つかりません。 引数 szSqlStr に、存在しない列名を参照 する SQL ステートメントが含まれています。
44000 保全性制約違反です。 引数 szSqlStr に、パラメーターまたはリテラルのある SQL ステートメントが 含まれていますが、以下いずれかの違反があります。
  • NOT NULL として関連した表の列に定義されている列に対して、パラメーター値は NULL です。
  • 固有値しか持てないように制限されている列に対して、重複した値が与えられました。
  • 整合性の制約に違反しています。
580 04 予想外のシステム障害が発生しました。 リカバリー不能なシステム・エラーです。
HY001 メモリーの割り振りが失敗しました。 DB2 ODBC は、関数の実行または完了をサポートするのに必要なメモリーを割り振ることができません。
HY009 NULL ポインターの使用が無効です。 引数 szSqlStr が NULL ポインターを指定しています。
HY013 予期しない、メモリーのハンドル・エラーです。 DB2 ODBC は、関数の実行または完了をサポートするのに必要なメモリーにアクセスすることができません。
HY014 これ以上ハンドルがありません。 DB2 ODBC は、内部リソースが少ないため、ハンドルを割り振ることはできません。
HY019 数値が範囲外です。 次の 1 つ以上の理由に該当した場合に、この SQLSTATE が戻されます。
  • 割り当て時もしくは中間結果の計算時に、数字タイプ列に割り当てられた数値が原因で、 数値の整数部分が切り捨てられました。
  • 引数 szSqlStr は算術式を伴う SQL ステートメントを持っていますが、 それが除数ゼロで割り算を行いました。
HY090 ストリングまたはバッファーの長さが無効です。 引数 cbSqlStr は 1 より小さい値です が、SQL_NTS と等しくありません。
注:
  1. xxx は、そのクラス・コードの任意の SQLSTATE を表します。 例えば、37xxx は、クラス・コード '37' の 任意の SQLSTATE を表しています。

関連例については、SQLFetch() を参照してください。