トランザクションメッセージング
トランザクションメッセージングは、ローカルステートの変更(データベース/キャッシュ)とブローカー/バス上のメッセージ間の一貫性を確保するアーキテクチャ技術のセットです。目的:「状態は固定されます↔メッセージは失われませんまたは重複していません」失敗の場合、リトレイ、スケーリングとマルチテナンシー。
1)配信セマンティクス
At-once:迅速かつ安価な、可能な損失、取ることはありません。
少なくとも一度:メッセージを失うことはありません、重複が可能です→idempotencyが必要です。
(効果的)正確に一度:技術の組み合わせ(アウトボックス/受信トレイ、生産者/消費者取引、デッドアップ)によって達成された、ビジネス効果のための損失や目に見えるテイクはありません。
2)なぜ「二文字」が危険なのか
Naiveロジック「最初にデータベースに書き込み、次にバスに送信」(またはその逆)ステップの間に落ちたときに壊れます:データは固定され、イベントは失われます。イベントがなくなってもデータはありません。トランザクションメッセージングはこのギャップを埋めます。
3)基本パターン
3.1アウトボックス(メーカー)
1つのローカルトランザクションでは、ビジネスの変更と行を'outbox'テーブルに書き込みます。別のパブリッシャーはアウトボックスを読み、レトラとバックオフを持つブローカーで発行します。除外された損失;二重は消費者の間のidempotencyによって消されます。
3.2受信トレイ/Idempotent Consumer
エフェクトを実行する前に、消費者は「inbox (consumer、 event_id)」に「INSERT」を主キーとして作成します。キーコンフリクト=既に処理されているイベント→スキップ。これが「効果的に一度」を達成する方法です。
3.3オフセットトランザクションによる読み取りプロセス書き込み
ログ指向のバスのテンプレート:消費者はバッチを読み取り、同じトランザクションでビジネスの変更と「渡されたオフセット」を記録します。"コミット後、ブローカーは消費されたメッセージを考慮します。これにより、エフェクトの重複なしに「read→fall→repeat」が排除されます。
3.インターサービスエフェクトのための4つのTSS/Sagas
一貫したマルチステッププロセスが必要な場合は、TCCまたはサガを使用してください。メッセージ-コマンド/イベントの転送、トランザクション性-ステップと補償のレベルで。
4) Idempotent生産者および消費者
Producer: stable 'message_id'/'idempotency_key'、同じキーで再送すると購読者に新しいエフェクトが作成されません。キーごとにシーケンスを維持します。
Consumer: 'inbox'+business idempotency (upsert/merge、 check latest version/revision)。
5)秩序と因果関係
ビジネスキー(例えば、'aggregate_id'、 'tenant_id')によって参加し、1つのオブジェクトのイベントが順番に到着するようにします。
ロット内の連続した数字/タイムスタンプを保持します。DLQから再描画する場合は「、キーと順番に」観察してください。
グローバル注文が重要でない場合は、キーによるローカル注文を確認し、ドメイン不変量を修正します。
6)オフセットおよび固定効果
オプションA: 「DBでオフセット」
「最後に処理されたオフセット(パーティション、オフセット)」を、ドメインデータを変更する同じトランザクションに書き込みます。再起動するときは、次のオフセットから続けて、繰り返し効果を避けます。
オプションB: ブローカー取引
一部のブローカーは、1つの生産者/消費者取引におけるメッセージとオフセットの原子記録をサポートしています。利用可能であれば使用してください、しかし、常に消費者のidempotencyと補足。
7)レトライ、バックオフ、DLQ
リトラクタブルエラー(タイムアウト、5xx)のみを繰り返し、指数関数バックオフとジッタを使用します。
取り消し不可(スキーマ/検証)-すぐにDLQでメタデータ(テナント、キー、オフセット、理由)。
DLQ(バッチ、レート制限)から再ドレーブを投与し、繰り返し前に回路を確認し、キーで順序を観察します。
8)複数のテナントおよび地域
メッセージメタデータとパーティションキーに'tenant_id'、 'plan'、 'region'を含める。
テナントごとの公平性:「騒々しい」クライアントが残りから予算を差し引かないように、発行/処理を制限します。
レジデンシー:ドメインデータと同じ領域にメッセージとアウトボックスを保存します。地域間レプリケーション-非同期集計。
9)観察可能性および監査
トレース:相関'event_id'/'aggregate_id'/'saga_id'、 「read→process→write/commit」。
メトリクス:発行/処理遅延(p95/p99)、成功率、DLQ率、再帰成功、「重複抑制」。
ログ:成功のための短い;エラーの詳細(理由、試行、キー、オフセット)。
監査:誰が再描画/ロールバック、どのようなバッチとどのような結果で。
10)安全性とコンプライアンス
ペイロードのPIIを最小化します。DLQ/ログに転送するときにマスクします。
外部バスのための署名/暗号化メッセージ。サービス間でmTLSを使用します。
テナント/地域ごとに保存期間と「忘れる権利」を管理します。
11)典型的な統合スキーム
1.サービスソース(書き込み側)
ローカルトランザクション:ドメインレコード+アウトボックス。
出版社:バッチ、'SKIP LOCKED'、バックオフ、テナントごとの制限。
モニタリング遅延− occurred_at'。
2.サービス消費者(読み取り側)
バッチ→"INSERT inbox (consumer、 event_id)"→"成功するとエフェクトを実行します。
同じトランザクションで「、渡されたオフセット」(オプションA)を修正するか、ブローカーのトランザクション(オプションB)に依存します。
エラーの場合:ポリシーによる再試行またはDLQ。
3.投影/具体化ビュー
idempotent updates (upsert)、コンパクトな重複除外キー、定期的なチェックサム検証のみ。
12)コンフィギュレーションテンプレート(例)
yaml producer:
idempotency_key: event_id partition_key: "{tenant_id}:{aggregate_id}"
retry:
max_attempts: 8 initial_ms: 200 max_ms: 8000 strategy: exponential_full_jitter
consumer:
batch: 500 offset_commit: "with_domain_tx" # или "broker_tx"
inbox_enabled: true concurrency_per_partition: 4 dlq:
enabled: true batch_redrive: 200 rate_limit_per_sec: 50 order_by_key: true
observability:
metrics:
- processing_lag_ms
- publish_success_ratio
- dlq_rate
- redrive_success_ratio tracing_tags: [event_id, tenant_id, aggregate_id, partition, offset]
13)売り上げ前のチェックリスト
- 「2文字」を排除:生産者のアウトボックスまたは消費者の1つのトランザクションでのオフセットとエフェクトを修正します。
- Idempotent consumer: 'inbox '/dedup journal、業務のidEmpotency。
- ビジネスキーによるパーティショニング、ローカル注文に従います。
- バックオフ+ジッタのリトレース、エラー分類、メタデータの豊富なDLQ。
- 再ドレーブ投与、安全;Playbookがあります。
- マルチテナントの制限と優先順位;'tenant_id/plan/region'タグ。
- テレメトリー:ラグ、成功率、「重複抑制」、p95/p99によるアラート。
- PII/retention/暗号化ポリシーが適用されます。
- テスト:ステップ間のドロップ、重複、キー順序、大量再描画。
14)典型的なエラー
バスに送信し、outbox/offsetトランザクションなしで別のステップでデータベースに書き込みます。
idempotency→duplicates副作用のない消費者。
グローバルな秩序「来るかもしれないもの」は高価であり、ほとんど正当化されません。キーによる十分な順序。
制限のない大規模な再描画→二次インシデント。
トレース/ラグのメトリックがない→「隠れた劣化」
DLQ/ログのPIIミキシング。
15)クイックレシピ
SaaSイベント:Outbox+idempotent consumer (inbox)、 partitioning by 'tenant_id: aggregate_id'。
ETL/投影: 1つのトランザクション、バッチ500-1000、 upsertの固定オフセットとの読み取りプロセス書き込み。
高負荷:パブリッシングシャーディング、'SKIP LOCKED'、テナントごとのWFQ、ラグコントロール。
厳格なコンプライアンスゾーン:リージョナルアウトボックス、ペイロード暗号化、リテンションおよびレドライブの監査。
結論
トランザクションメッセージングは、データとメッセージを接続する規律です。outbox/inbox、 idempotency、オフセット固定、エフェクト、マネージドリトレイをDLQと組み合わせることで、グローバルロックなしで正確に一度の動作を実現し、クラッシュ、ピーク、複雑なマルチテナント攻撃でもSLOを維持できます。