テクノロジー · 実用ガイド
PostgreSQLで「current transaction is aborted」?再試行前に最初のエラーを特定する
SQLSTATE 25P02 は先行する失敗の結果として扱い、最初の SQLSTATE、接続、トランザクション所有者を保存してから、全体のロールバックか失敗前のセーブポイントかを選びます。

PostgreSQL の「current transaction is aborted」は、多くの場合、同じトランザクション内で先に起きた文の失敗の結果です。最後の文を繰り返しても直らず、根本原因を隠すことがあります。
安全な順序は、最初のエラーを保存し、正確な接続と所有者に結び付け、有効な回復分岐を選び、再試行やプール返却の前に接続を検証することです。
回復前に最初の失敗を固定する
25P02 は、同じトランザクションの前の文が失敗し、回復まで後続コマンドが無視される状態を示します。最初のサーバーエラー、SQLSTATE、安全な文フィンガープリント、時刻、スタックを保存してから回復します。
最初に見える行がすでに 25P02 なら、同じ接続の前方へログ範囲を広げ、クライアント生成文、トリガー、制約違反、先行例外を確認します。
接続とトランザクション境界を証明する
アプリケーション、プール、接続 ID、DB ユーザー、バックエンド PID、自動コミット、開始時刻を記録します。要求と接続は一対一とは限りません。
BEGIN、ORM、マイグレーション、ノートブック、DB クライアント、暗黙トランザクションのどれが所有者か確認します。Psycopg は autocommit が無効なら SELECT でも既定でトランザクションを開始します。
安全なセーブポイントがなければ全体をロールバック
作業を破棄できるなら、ドライバーまたはフレームワークの rollback を呼び、失敗状態を抜けたことを確認してから再試行します。未清掃の接続をプールへ戻すと、次の要求へ症状が移ります。
全体のロールバックは未コミット変更をすべて取り消します。失われる作業と所有者を記録し、COMMIT でエラーを消そうとしないでください。
セーブポイントは危険な処理より前に必要
失敗前に作成したセーブポイントだけが、それ以前の作業を保持できます。ROLLBACK TO SAVEPOINT で回復し、その後に継続または解放を判断します。25P02 の後で新規作成しても遅すぎます。
中止中は RELEASE SAVEPOINT を実行できません。フレームワーク管理のセーブポイントは、その API を使って状態を同期させます。
プール、ORM、DB クライアントの隠れた文を監査
ヘルスチェック、件数取得、メタデータ照会、コールバック、自動 flush が表示 SQL より先に走っていないか確認します。DBeaver の事例は需要の証拠であり、同じ製品不具合の断定材料ではありません。
返却時は commit または rollback を明示し、アイドル状態を確認します。ORM では上位例外に包まれる前の最初の DB エラーを保存します。
最後の文ではなく作業単位を再試行
最初の原因を修正し、定義済み境界から最小の冪等な業務単位を再試行します。最後の文だけを再実行すると、DB 外の副作用を重複させる可能性があります。
再試行可能性は最初の SQLSTATE で分類します。制約違反は入力修正、一時的な競合は上限付き再試行、権限エラーは設定修正が必要です。
サービスへ戻す前にクリーン状態を検証
同じフレームワーク経路で無害な確認を行い、次のトランザクションが正常に開始・終了するか、プールのリセット記録または接続状態で確かめます。
最初の SQLSTATE、所有者、接続 ID、回復分岐、失われた作業、再試行判断、予防策を記録して完了します。
