Webエンジニア向けプログラミング解説動画をYouTubeで配信中!
▶ チャンネル登録はこちら

【ITニュース解説】We replayed failed payouts after the provider had forgotten them

2026年10月12日に「Dev.to」が公開したITニュース「We replayed failed payouts after the provider had forgotten them」について初心者にもわかりやすく解説しています。

作成日: 更新日:

ITニュース概要

決済プロバイダーAPI連携でタイムアウトが発生。週末を挟んで再送した際、冪等性キーの24時間有効期限が切れ、二重支払いが発生した。これを受け、再送前にプロバイダーへの確認を必須化。デッドレターキューにも期限チェックを導入し、同様の問題再発防止策を講じた。

ITニュース解説

ある企業が直面した支払いシステムにおけるトラブル事例を解説する。この事例は、システム間の連携やデータの整合性、そしてドキュメントの重要性について多くの教訓を与えるものである。

この企業は、自社のサプライヤーへの支払いを、外部の支払いプロバイダが提供するAPIを通じて行っていた。APIとは、異なるソフトウェア同士がデータのやり取りや機能の呼び出しを行うための仕組みである。これにより企業は、自前で複雑なシステムを構築することなく専門サービスを利用できる。支払いリクエストを送る際、この企業は「べき等性キー」という特別な識別子を毎回含めていた。べき等性とは、同じ操作を何回実行しても結果が一度実行した場合と同じになる性質である。支払い処理の場合、ネットワークの不具合などで同じリクエストが複数回送られても、べき等性キーによってプロバイダはそれを認識し、二重支払いを防ぐ。これは、信頼性の高いシステムを構築する上で非常に重要である。

しかし、ある金曜日の夜に問題が発生した。支払いプロバイダ側で部分的な障害が起こった。これは、システム全体が完全に停止するのではなく、一部の機能に問題が生じる状態を指す。このケースでは、プロバイダのAPIは支払いリクエスト自体は受け付け、内部で処理も実行したが、その結果を企業側に返送することができなかった。企業側のシステムは、プロバイダからの応答を30秒間待ったが、応答がなかったため「タイムアウト」と判断し、処理を打ち切った。システムは自動的に同じリクエストを3回まで「リトライ」、つまり再試行するように設定されていたが、3回ともタイムアウトした。最終的に、これらの未解決のリクエストは「デッドレターキュー」という特別な場所に移動された。デッドレターキューは、処理に失敗したり、リトライしても解決しなかったりしたメッセージを一時的に保管し、後で人間が確認したり、手動で再処理したりするために使われる。

週末が明け、月曜日の朝に担当者がデッドレターキューの内容を確認した。プロバイダの「ステータスページ」を確認したところ、インシデントはすでに解決済みと表示されていたため、担当者はキューに入っていた380件の支払いを、すべて同じべき等性キーを使って再送信した。しかし、ここで問題が起こった。再送信された380件の支払いはすべてプロバイダに受け付けられ、実行されたが、そのうち229件はすでに金曜日の障害発生時に一度支払いが完了していたものだった。つまり、意図しない「二重支払い」が発生してしまったのである。

なぜこのような二重支払いが起こったのか。その原因は、支払いプロバイダの「ドキュメント」の中にあった重要な情報を見落としていたことと、システムの設計思想の齟齬にあった。プロвайダのドキュメントには、「べき等性キーは24時間保持される」と明確に記載されていた。これは、24時間を過ぎると、たとえ同じべき等性キーが送られてきても、プロバイダはそのキーを「初めて見る文字列」として扱い、新しい支払いリクエストとして処理してしまうことを意味する。今回のケースでは、金曜日の障害発生から月曜日の再送信まで約60時間経過しており、べき等性キーの有効期限を大幅に過ぎていたのである。

この企業は、システムを構築する際にこの24時間という期限に関する記述を読んでいたが、自動リトライが通常数分以内に完了するため、この情報を「些細な詳細」として重要視していなかった。しかし、デッドレターキューは、人が手動で確認するまでの間、リクエストを何時間でも待機させることを目的として設計されている。手動で再送信を行った担当者も、べき等性キーに有効期限があることを知らなかったため、期限切れのキーで再処理してしまった。この結果、総額19万ポンド(日本円で約3500万円)という多額の二重支払いが発生した。幸いにも、サプライヤーとの3週間にわたる交渉の末、約4000ポンドを除くほとんどの金額を回収することができたが、大きな手間と損失を伴った。

この経験から、企業は再発防止のために複数の対策を講じた。まず、プロバイダからの応答がタイムアウトした場合、そのリクエストを「失敗」ではなく「不明」な状態として扱うことにした。そして、不明なリクエストを再度送信する前に、必ずプロバイダのAPIを使って、自社が持つ「参照ID」で該当の支払い状況を事前に確認するように変更した。参照IDは、企業が個々の支払いを識別するために使うIDで、支払いリクエストの「メタデータ」、つまり追加情報としてプロバイダに送っていたものである。この確認作業により、プロバイダ側にすでに支払い記録がある場合は再送信を行わない。

さらに、デッドレターキュー内のメッセージに対しても改善を加えた。それぞれのメッセージには、それがキューに入ってからどれくらいの時間が経過したかを示す「年齢」が表示されるようになった。そして、再送信ツールは、20時間以上経過したメッセージで、かつ事前確認のステップを通過していないものは自動的に再送信を拒否するように変更された。これは、べき等性キーの24時間という有効期限を考慮し、再送信までの安全なマージンを設けるためである。

また、手動での確認だけでなく、システム的な確認体制も強化した。毎日、「日次照合」という処理を実行し、プロバイダが持つ支払いリストと自社の支払いリストを自動的に比較するようにした。これにより、万が一二重支払いが発生した場合には、早期にそれを検出し、対象のサプライヤーを特定できるようになった。

この一連の出来事は、「べき等性」という概念が単なる技術的な仕組みではなく、「期限付きの約束」であることを浮き彫りにした。その期限は、キーを保持する側、つまり支払いプロバイダによって設定されている。この企業は、リクエストを待機させるためのデッドレターキューと、期限付きのべき等性キーの特性を十分に考慮していなかったため、問題が発生した。システム設計においては、各コンポーネントの特性や、外部サービスとの契約内容(ドキュメントに記載された有効期限など)を深く理解し、それらを総合的に考慮した上で全体の仕組みを構築することの重要性を痛感させる事例である。

関連コンテンツ

関連IT用語