エラー処理

ECPGPlusは、埋め込みSQLコードのエラーを検出して処理するための2つの方法を提供します。

  • クライアントアプリケーションは、エラーメッセージの sqlca データ構造を調べ、クライアントアプリケーションにカスタマイズされたエラー処理を提供できます。

  • クライアントアプリケーションには、ECPGPlusコンパイラにエラー処理コードを追加するよう指示する EXEC SQL WHENEVER ディレクティブを含めることができます。

sqlcaでのエラー処理

sqlca (SQL通信領域)は、 ecpglib がサーバーからクライアントアプリケーションに情報を伝達するために使用するグローバル変数です。SQLステートメント( INSERT または SELECT ステートメントなど)を実行した後、 sqlca の内容を調べて、ステートメントが正常に完了したか、ステートメントが失敗したかを判断できます。

sqlca の構造は次のとおりです。

struct
{
    char sqlcaid[8];
    long sqlabc;
    long sqlcode;
    struct
    {
        int sqlerrml;
        char sqlerrmc[SQLERRMC_LEN];
    } sqlerrm;
    char sqlerrp[8];
    long sqlerrd[6];
    char sqlwarn[8];
    char sqlstate[5];

} sqlca;

次のディレクティブを使用して、 sqlca 機能を実装します。

EXEC SQL INCLUDE sqlca;

ecpg ディレクティブを含める場合、クライアントアプリケーションのヘッダー宣言に sqlca.h ファイルを #include する必要はありません。

AdvancedServerの sqlca 構造には、次のメンバーが含まれます。

sqlcaid

sqlcaid には文字列 /"SQLCA/" が含まれます。

sqlabc

sqlabc には sqlca 構造のサイズが含まれます。

sqlcode

sqlcode メンバーはSQL92で非推奨になりました。AdvancedServerは下位互換性のために sqlcode をサポートしますが、新しいコードを記述するときは sqlstate メンバーを使用する必要があります。

sqlcode は整数値です。正の sqlcode 値は、クライアントアプリケーションが無害な処理条件に遭遇したことを示し、負の値は警告またはエラーを示します。

ステートメントがエラーなしで処理される場合、 sqlcode には 0 の値が含まれます。クライアントアプリケーションがステートメントの実行中にエラー(または警告)に遭遇した場合、 sqlcode には最後に返されたコードが含まれます。

SQL標準では、正の値100のみが定義されています。これは、処理された最新のSQLステートメントが返された/影響を受けた行がないことを示します。標準SQLでは他の sqlcode 値を定義していないため、各条件に割り当てられる値はデータベースごとに異なる可能性があることに注意してください。

sqlerrm は sqlca 内に埋め込まれた構造で、2つのメンバーで構成されます。

sqlerrml

sqlerrml には、 sqlerrmc に現在保存されているエラーメッセージの長さが含まれます。

sqlerrmc

sqlerrmc には、 sqlstate に保存されているコードに関連付けられたヌル終了メッセージテキストが含まれます。メッセージの長さが149文字を超える場合、 ecpglib はエラーメッセージを切り捨てます。

sqlerrp

sqlerrp には /"NOT SET/" という文字列が含まれます。

sqlerrd は、6つの要素を含む配列です。

sqlerrd[1] には、処理された行のOIDが含まれます(該当する場合)。

sqlerrd[2] には、処理または返された行の数が含まれます。

sqlerrd[0], sqlerrd[3], sqlerrd[4] と sqlerrd[5] は未使用です。

sqlwarn は8文字を含む配列です。

sqlwarn 内の他の要素が 'W' に設定されている場合、 sqlwarn[0] には 'W' の値が含まれます。

データ値がホスト変数に格納されたときに切り捨てられた場合、 sqlwarn[1] には 'W' の値が含まれます。

クライアントアプリケーションが致命的でない警告を検出した場合、 sqlwarn[2] には 'W' の値が含まれます。

sqlwarn[3], sqlwarn[4], sqlwarn[5], sqlwarn[6] および sqlwarn[7] は未使用です。

sqlstate

sqlstate は、クライアントアプリケーションからステートメントを実行した後のSQL準拠のステータスコードを含む5文字の配列です。ステートメントがエラーなしで処理される場合、 sqlstate には 00000 の値が含まれます。 sqlstate はヌル終端文字列ではないことに注意してください。

sqlstate コードは階層スキームで割り当てられます:

  • sqlstate の最初の2文字は、条件の一般的なクラスを示します。

  • sqlstate の最後の3文字は、クラス内の特定のステータスを示します。

クライアントアプリケーションがSQLステートメントの実行中に複数のエラー(または警告)に遭遇した場合、 sqlstate には返された最後のコードが含まれます。

次の表に、 sqlstate と sqlcode の値、および関連する条件のシンボル名とエラーの説明を示します。

sqlstate

sqlcode

(非推奨)

記号名

説明

YE001

-12

ECPG_OUT_OF_MEMORY

仮想メモリが枯渇しています。

YE002

-200

ECPG_UNSUPPORTED

プリプロセッサが認識されないアイテムを生成しました。プリプロセッサとライブラリ間の非互換性を示している可能性があります。

07001、または07002

-201

ECPG_TOO_MANY_ARGUMENTS

プログラムは、コマンドが予想するよりも多くの変数を指定します。

07001、または07002

-202

ECPG_TOO_FEW_ARGUMENTS

プログラムが指定した変数がコマンドの予想よりも少ない。

21000

-203

ECPG_TOO_MANY_MATCHES

SQLコマンドは複数の行を返しましたが、ステートメントは単一の行を受け取る準備ができていました。

42804

-204

ECPG_INT_FORMAT

ホスト変数(Cコードで定義されている)はINT型であり、選択されたデータはINTに変換できない型です。ecpglibは、strtol()関数を使用して文字列値を数値形式に変換します。

42804

-205

ECPG_UINT_FORMAT

ホスト変数(Cコードで定義)は符号なしINTであり、選択されたデータは符号なしINTに変換できないタイプです。ecpglibは、strtoul()関数を使用して文字列値を数値形式に変換します。

42804

-206

ECPG_FLOAT_FORMAT

ホスト変数(Cコードで定義)はFLOAT型であり、選択されたデータはFLOATに変換できない型です。ecpglibはstrtod()関数を使用して、文字列値を数値形式に変換します。

42804

-211

ECPG_CONVERT_BOOL

ホスト変数(Cコードで定義)はBOOL型であり、選択したデータをBOOLに保存することはできません。

YE002

-2-1

ECPG_EMPTY

サーバーに送信されたステートメントは空でした。

22002

-213

ECPG_MISSING_INDICATOR

サーバーから返されたNULL値にNULLインジケーター変数が指定されていません(クライアントアプリケーションが予期しないNULL値を受信しました)。

42804

-214

ECPG_NO_ARRAY

サーバーは配列を返しました。対応するホスト変数は配列を格納できません。

42804

-215

ECPG_DATA_NOT_ARRAY

サーバーは、配列値を予期するホスト変数に配列ではない値を返しました。

08003

-220

ECPG_NO_CONN

クライアントアプリケーションは、存在しない接続を使用しようとしました。

YE002

-221

ECPG_NOT_CONN

クライアントアプリケーションは、割り当てられたが閉じられた接続を使用しようとしました。

26000

-230

ECPG_INVALID_STMT

ステートメントは準備されていません。

33000

-240

ECPG_UNKNOWN_DESCRIPTOR

指定された記述子が見つかりません。

07009

-241

ECPG_INVALID_DESCRIPTOR_INDEX

記述子のインデックスが範囲外です。

YE002

-242

ECPG_UNKNOWN_DESCRIPTOR_ITEM

クライアントアプリケーションが無効な記述子項目を要求しました(内部エラー)。

07006

-243

ECPG_VAR_NOT_NUMERIC

動的ステートメントが、非数値ホスト変数の数値を返しました。

07006

-244

ECPG_VAR_NOT_CHAR

動的SQLステートメントがCHAR値を返しましたが、ホスト変数はCHARではありません。

/

-400

ECPG_PGSQL

サーバーがエラーメッセージを返しました。結果のメッセージにはエラーテキストが含まれます。

08007

-401

ECPG_TRANS

サーバーは、指定されたトランザクションを開始、コミット、またはロールバックできません。

08001

-402

ECPG_CONNECT

クライアントアプリケーションがデータベースに接続しようとして失敗しました。

02000

100

ECPG_NOT_FOUND

最後のコマンドが行を取得または処理しなかったか、カーソルの終わりに達しました。

EXECSQLWHENEVER

EXEC SQL WHENEVER ディレクティブを使用して、ECPGPlusでコンパイルされたクライアントアプリケーションに簡単なエラー処理を実装します。ディレクティブの構文は次のとおりです。

EXEC SQL WHENEVER <condition> <action>;

このディレクティブは、エラー処理コードをプログラムに挿入するようにECPGコンパイラーに指示します。

このコードは、クライアントアプリケーションが特定の条件を検出した場合に、指定されたアクションを実行するようにクライアントアプリケーションに指示します。条件 は次のいずれかです。

SQLERROR

sqlca.sqlcode がゼロ未満の場合、 SQLERROR 条件が存在します。

SQLWARNING

sqlca.sqlwarn[0] に 'W' が含まれる場合、 SQLWARNING 条件が存在します。

NOT FOUND

sqlca.sqlcode が ECPG_NOT_FOUND の場合(クエリがデータを返さない場合)、 NOT FOUND 条件が存在します。

前の条件のいずれかに遭遇した場合、クライアントアプリケーションが次の*アクション* のいずれかを実行するように指定できます。

CONTINUE

CONTINUE を指定して、現在の condition を無視して、クライアントアプリケーションに処理を続行するよう指示します。 CONTINUE がデフォルトのアクションです。

DO CONTINUE

DO CONTINUE のアクションは、放出されたCコードに CONTINUE ステートメントを生成します。条件に遭遇すると、ループ内の残りのコードをスキップし、次の反復を続行します。ループ内でのみ使用できます。

GOTO label

または

GO TO label

Cの goto ステートメントを使用して、指定した label にジャンプします。

SQLPRINT

sqlprint() 関数を使用して、エラーメッセージを stderr (標準エラー)に出力します。 sqlprint() 関数は sql error を出力し、その後に sqlca.sqlerrm.sqlerrmc の内容が続きます。

STOP

exit(1) を呼び出してエラーを通知し、プログラムを終了します。

DO BREAK

Cの break ステートメントを実行します。このアクションは、ループまたは switch ステートメントで使用します。

CALL name(args)

または

DO name(args)

args パラメーターで指定されたパラメーターを使用して、 parameter という名前で指定されたC関数を呼び出します。

Example:

次のコードは、クライアントアプリケーションで警告が発生した場合にメッセージを出力し、エラーが発生した場合にアプリケーションを中止します。

EXEC SQL WHENEVER SQLWARNING SQLPRINT;
EXEC SQL WHENEVER SQLERROR STOP;

注釈

クライアントアプリケーションが上から下に*実行* できない場合でも、ECPGPlusコンパイラはプログラムを上から下に処理します。コンパイラ指令は各行に順番に適用され、コンパイラが別の指令に遭遇するまで有効です。プログラム内のフローの制御が上から下にない場合は、コンパイル中に誤って見落とされる可能性のあるプログラムの部分にエラー処理ディレクティブを追加することを検討する必要があります。