transaction-consistency-designer について
業務ワークフローのトランザクション境界を設計する開発スキルです。Kotlin + Spring の整合性を検討する開発者向けに、不変条件や失敗経路を起点として、冪等性、並行性、外部副作用を扱います。
主な機能
- 01状態変更と外部副作用の分解
- 02業務不変条件に基づく境界設定
- 03伝播設定と分離レベルの評価
- 04冪等性、ロック、再試行の設計
- 05整合性を確認するテストの計画
活用シーン
- 01DB 書き込みと外部呼び出しを含む処理のレビュー
- 02再試行による副作用の重複防止
- 03ロールバック、重複リクエスト、競合処理の検証
インストール
コマンドをコピーしてターミナルで実行します。
$
npx skills add https:/ / github.com/ jetbrains/ skills --skill transaction-consistency-designerインストール後、Claude Code で/transaction-consistency-designerを入力して読み込まれたか確認します。
同梱ファイルagents/openai.yaml
詳細
トランザクション整合性の設計
ソースマッピング:Kotlin_Spring_Developer_Pipeline.md(SK-09)に基づく Tier 1 の重要なスキルです。
ミッション
アノテーションを手軽に書ける場所ではなく、ビジネス不変条件が実際に適用される場所にトランザクション境界を設定します。 データ損失、重複した副作用、潜在的な整合性の不具合を防ぎます。
収集する入力情報
- ビジネスワークフローの各ステップ。
- 各ステップで使用するリポジトリとテーブル。
- 現在の
@Transactionalアノテーション、伝播設定、分離レベル、例外処理。 - ワークフロー内で行われる外部HTTP通信、メッセージブローカー、スケジューラー、ファイルI/O。
- 冪等性、再試行、並行性に関する要件。
ワークフローを明示的にモデル化する
- ユースケースを、状態を変更するステップと副作用に分けます。
- どのステップをまとめてアトミックに実行する必要があり、どのステップを非同期にできるかを明確にします。
- 外部システムを呼び出す箇所を明確にします。
- 再試行が発生し得る箇所を明確にします。
- 違反してはならないビジネス不変条件を明確にします。
判断ルール
- 1つのデータベーストランザクションは、1つの整合性境界に集中させます。
- 外部ネットワーク呼び出しの間、データベーストランザクションを開いたままにすることは避けます。
- 重複リクエストへの安全性には、冪等性キーと一意制約の組み合わせを優先します。
- コミット済みの状態を反映する必要があるメッセージには、アウトボックスパターンまたはコミット後のパブリッシュを優先します。
- ロック方式は、競合の頻度と正確性の要件に基づいて選びます。
- 競合頻度の低い更新競合には楽観的ロック
- 重複の防止には一意制約
- 悲観的ロックは、競合の頻度と正確性の要件から正当化される場合に限る
Spring 固有の確認事項
@Transactionalがプロキシ化された公開エントリーポイントに付与されているか確認します。- 自己呼び出しによってトランザクション境界が迂回されないか確認します。
- ロールバックのルールを確認します。デフォルトでは、非検査例外はロールバックされますが、検査例外はロールバックされない場合があります。
readOnly = trueが適切な箇所でのみ使用されているか確認します。REQUIRES_NEWが本当に必要なのか、それとも設計上の問題を覆い隠しているのか確認します。NESTEDはデータベースやプラットフォームに依存する設定であり、あらゆる問題に使える回避策ではないことを前提にします。
指摘すべきアンチパターン
- デフォルトでコントローラーに
@Transactionalを付与する。 - データベースへの書き込み後に時間のかかるHTTP呼び出しを行う、1つのトランザクション。
- トランザクション内で例外を捕捉し、成功したかのようなフローに変換する。
- コミット前に取り消せない副作用を発生させる。
- 冪等性を確保せずに再試行が安全だと想定する。
- 境界が不明確な問題を隠すために、より強い伝播設定を使う。
高度な整合性に関する注意点
- 重複防止と並行性制御を区別します。一意制約で解決できるのは特定の種類の競合であり、更新の消失や書き込みスキューではありません。
- 多くの整合性違反は、エンティティを変更した行ではなく、フラッシュまたはコミット時に初めて発生します。それを踏まえてテストと例外処理を設計します。
UnexpectedRollbackExceptionは、外側のレイヤーが成功を返そうとしたにもかかわらず、内側の処理がトランザクションをロールバック専用としてマークしたことを示す場合がよくあります。- 分離レベルの実際の効果はデータベースによって異なります。Postgres、MySQL、SQL Serverでは、同じ設定でも防止できる異常が異なる場合があります。
- デッドロックやシリアライゼーション失敗の再試行は、慎重に選んだ外側の境界で行います。外部の副作用が発生した後で、半分実行されたワークフローを再試行するのは危険です。
@TransactionalEventListenerとTransactionSynchronizationの動作はフェーズに依存します。コミット前、コミット後、ロールバック後のどのタイミングで動かすかを意図的に選びます。- ワークフローがサービス境界をまたぐ場合は、ローカルトランザクションの設計とサーガまたはオーケストレーションの設計を区別します。1つのローカルトランザクションで分散整合性を保証できるかのように扱ってはいけません。
- リアクティブまたはコルーチンのトランザクションフローでは、実際に使われているトランザクションマネージャーとコンテキスト伝播モデルを確認します。命令型の前提が通用しないことがよくあります。
専門家のヒューリスティック
- アノテーションではなく、不変条件から始めます。ユーザーや下流システムから見て、決して偽になってはならないことを考えます。
- 一意性やあり得ない状態の防止には、データベースで強制できる不変条件を優先し、そのうえでアプリケーションロジックを使って違反を起こりにくくし、発生した場合にも理解しやすくします。
- ワークフローにコマンド処理とクエリ処理が混在する場合、書き込み直後の読み取りがすぐに保証される必要があるのか、それとも結果整合性で許容できるのかを判断します。
- チームが
REQUIRES_NEWを求める場合、監査ログを分離したいのか、ロールバックの動作を覆い隠したいのか、それともより大きな設計上の問題を補おうとしているのかを確認します。
出力仕様
次のセクションを返します。
整合性の目標:保護するビジネス上の不変条件。推奨される境界:メイントランザクションの開始位置と終了位置。伝播と分離レベル:重要な設定のみを、その理由とともに示します。冪等性と並行性:重複処理、ロック、再試行の安全性。外部への副作用:トランザクションの外で行うべき処理、またはアウトボックス方式で行うべき処理。検証:ロールバック、重複処理、競合時の動作を検証するテストやシナリオ。
ガードレール
- すべてのサービスメソッドに、デフォルトで
@Transactionalを付けないでください。 - プロジェクトですでに利用しており、真に必要な場合を除き、分散 2PC や XA を推奨しないでください。
- 外部呼び出し中にデータベース接続を保持するコストを無視しないでください。
- データベースで重複を防止できる場合、重複防止をアプリケーションだけの問題として扱わないでください。
品質基準
このスキルが適切に実行されると、曖昧なワークフローが明確な整合性境界と、検証可能な不変条件に落とし込まれます。
適切に実行されないと、失敗経路、再試行、副作用をモデル化せず、メソッドに @Transactional を付けるだけになります。
コメント
Markdown 対応