このセクションでは、MySQL互換アプリケーションのエラー処理規範について説明します。
OceanBaseデータベースはV1.0バージョンからMySQLデータベースとの完全な互換性を提供しています。エラーコードについては、エラーコード、SQLSTATE、エラーメッセージの3つの情報において、可能な限りMySQLデータベースとの一貫性を保証しています。したがって、当社の製品設計原則に基づき、アプリケーションのエラー処理方法はMySQLデータベースの処理規範を参考にすることができます。ただし、分散データベースとして、OceanBaseデータベースはスタンドアロンのMySQLデータベースとは本質的に異なり、分散環境特有の一部のエラーはMySQLデータベースのエラーコードでは表現できません。一般的に、エラーコードの値が4000を超える場合、そのエラーコードはOceanBaseデータベース固有のエラーコードであることを意味します。エラーコードの値が4000以下の場合、それはMySQLデータベースと互換のエラーコードであることを意味します。OceanBaseデータベースサーバー側のMySQLテナントモードにおける完全なエラーコード一覧については、エラー情報の概要を参照してください。
アプリケーションが検出するエラーは、データベースサーバー側から返されるエラーの他に、ドライバーライブラリがローカルで返すエラー(例:データベース接続の確立失敗)も含まれる可能性があります。OceanBaseデータベースのMySQLテナントを使用するアプリケーションはMySQLのドライバーライブラリ(例:MySQL JDBC Driver)を使用できるため、このようなエラーコードについては、OceanBaseデータベースはMySQLデータベースと完全に互換性があります。この種のクライアントエラーコードの値域は通常2000~3000です。
エラー情報の取得
各言語のドライバーは、エラー情報を取得するための異なるAPIを提供しています。各ドライバーの詳細については、OceanBaseデータベース公式ドキュメントおよびMySQLデータベース公式ドキュメントを参照してください。
Javaドライバーライブラリ
JDBCを使用するJavaアプリケーションがSQLステートメントの実行に失敗した場合、SQLException例外をキャッチできます。この例外にはエラーコード、SQLSTATE、エラーメッセージの3つの情報が含まれています。SQLException例外の詳細については、JDBC APIドキュメントを参照してください。
SQLException例外をキャッチする方法は以下のとおりです:
- getErrorCode()を呼び出してエラーコードを取得する
- getSQLState()を呼び出してSQLSTATEを取得する
- getMessage()を呼び出してエラーメッセージを取得する
libmysql Cドライバーライブラリ
libmysqlを使用するC言語アプリケーションがSQLステートメントの実行に失敗した場合、以下の方法でエラー情報を取得できます:
- mysql_errno()を呼び出してエラーコードを取得する
- mysql_sqlstate()を呼び出してSQLSTATEを取得する
- mysql_error()を呼び出してエラーメッセージを取得する
エラー処理規範
OceanBaseデータベースのMySQLテナントモードにおけるほとんどのエラーコードについて、アプリケーションは特別な処理を行う必要がなく、直接外部にエラーを報告できます。フォールトトレランスとアプリケーションの堅牢性を高めるため、特定のエラーコードについては、異なるシナリオやエラーの性質に応じて、以下の4つの異なる戦略を採用できます:
戦略1:ステートメントのタイプに基づいて処理します。
SELECTステートメントの実行時にタイムアウトエラーが発生した場合、副作用がないため、再試行できます。リモートまたは分散実行による
UPDATEなどの変更ステートメントでタイムアウトエラーが発生した場合、ステートメントが実際に実行されたかどうかは不確定であるため、トランザクションをロールバックする必要があります(変更ステートメントのセマンティクスが冪等である場合、そのステートメントの再試行を試みることができます)。COMMITまたはROLLBACKステートメントの実行時にタイムアウトエラーが発生した場合、トランザクションの状態が不明であるため、直接外部にエラーを報告する必要があります。
戦略2:任意のステートメントの実行でエラーが発生した場合、現在のトランザクションをロールバックしてから、トランザクションを再試行します。
戦略3:任意のステートメントの実行でエラーが発生した場合、現在のステートメントを再試行します。
戦略4:任意のステートメントの実行でエラーが発生した場合、現在の接続を閉じてから、接続を再確立します。
OceanBaseデータベース固有のエラーコード
以下のエラーコードは、一般的なOceanBaseデータベースサーバー固有のランタイム例外のエラーコードです。アプリケーションは、下表の異なるタイプのエラーコードに基づいて、「処理戦略」の推奨に従って処理できます。
エラーコード |
SQLSTATE |
意味 |
ステートメントの実行結果 |
トランザクション状態 |
処理戦略 |
|---|---|---|---|---|---|
| 4012 | HY000 | 実行タイムアウト | 不明 | 不明 | 戦略一 |
| 4038 | HY000 | 現在のレプリカがリーダーレプリカではないため、サービスを提供できません。通常、レプリカのリーダー切り替え時に発生する可能性があります。 | 失敗 | 不変 | 戦略三 |
| 4138 | HY000 | 読み取ったスナップショットバージョンが古すぎます | 失敗 | 不変 | 戦略三 |
| 4225 | HY000 | パーティションが存在しません。通常、パーティションの移行時に発生する可能性があります。 | 失敗 | 不変 | 戦略三 |
| 6002 | 40000 | トランザクションがシステム内部でロールバックされました | 失敗 | ロールバック済み | 戦略二 |
| 6231 | HY000 | レプリカデータが読み取り不可です。通常、レプリカの移行時に発生する可能性があります。 | 失敗 | 不変 | 戦略三 |
| 6235 | 25000 | 現在のトランザクションを直列化できません。通常、RR(Repeatable Read)およびSerializable分離レベルでトランザクションの並行競合が発生した場合に起こる可能性があります。 トランザクション分離レベルの詳細については、トランザクション分離レベルの概要を参照してください。 |
失敗 | 不変 | 戦略二 |
| 8001~8004 | 08004 | 接続を復元できません | 失敗 | 不明 | 戦略四 |
MySQL互換エラーコード
エラーコードが4000以下のMySQLデータベース互換エラーコードについては、MySQLデータベースと同じ処理方法に従ってください。特に、アプリケーションは以下のエラーコードに注意する必要があります。
エラーコード |
SQLSTATE |
意味 |
処理戦略 |
|---|---|---|---|
| 1205 | HY000 | デッドロックが検出されました | 現在のトランザクションをロールバックして再試行します |
| 1213 | 40001 | ロック待機タイムアウト | 現在のトランザクションをロールバックして再試行します |