よろずやIT
プログラミング

APIのタイムアウトとリトライの決め方|待ち時間・回数・間隔と、やってはいけない再試行

執筆・監修:よろずやIT編集部|編集方針を見る

結論:まずここだけ読めばOK

詳しい手順・原因は、この下で解説しています。

プログラミングのイラスト

決めていないと、何が起きるか

APIを呼ぶコードを書く時、「いつまで待つか」「失敗したら、何回やり直すか」を、決めていないことがあります。すると、次のような問題が起きます。

決めていないと 起きること
タイムアウトを、設定しない 相手が応答しない時に、いつまでも待ち続け、自分側のシステムが固まる
失敗したら、すぐ無限に再試行 相手が不調の時に、さらに負荷をかけ、アクセス制限を受ける
再試行で、二重処理 決済や登録が、二重に実行される

これらは、運用で障害が起きた時に、初めて表面化しやすい問題です。

タイムアウトの種類

「タイムアウト」には、いくつか種類があります。

種類 意味
接続のタイムアウト 相手に、接続できるまでに待つ時間の上限
読み取り(応答)のタイムアウト 接続した後、応答が返ってくるまでに待つ時間の上限
全体のタイムアウト リクエストの開始から終わりまでの、合計の時間の上限

使うライブラリによって、設定できる項目は異なります。必ず、何らかのタイムアウトを設定してください。初期値が「無制限」になっているライブラリも、あります。

値の決め方

観点 考え方
相手の通常の応答時間 通常、どれくらいで返ってくるかを、観察する
自分の許容できる待ち時間 利用者を待たせてよい上限から、逆算する
公式の推奨 相手のAPIの説明に、推奨値があれば、参考にする
処理の重さ 重い処理(大量のデータの取得など)は、長めにする

短すぎると、正常な処理が、失敗扱いになります。長すぎると、障害の時に、自分側が固まります。

再試行してよい失敗・いけない失敗

すべての失敗を、再試行すればよいわけではありません。

失敗の種類 再試行 理由
ネットワークの一時的なエラー、タイムアウト してよい 一時的な問題の可能性がある
429(リクエストが多すぎる) 待ってから、してよい 制限が解除されるのを待つ(レートリミットとは)
500番台(相手側の問題)、503 間隔をあけて、してよい 相手の復旧を待つ
400(リクエストが不正) しない 内容が同じなら、何度やっても失敗する
401・403(認証・権限) しない 認証情報や権限を、直す必要がある
404(見つからない) しない 宛先やIDが、誤っている可能性が高い

サービスによって、ステータスの使い方に違いがあるため、公式の説明も確認してください(API連携が「両方正常なのに繋がらない」時の確認5項目)。

間隔の決め方:指数バックオフとジッター

再試行の間隔は、失敗するたびに、延ばしていくのが基本です。これを指数バックオフと言います。たとえば、1秒、2秒、4秒、8秒、のように、倍々に延ばします。

さらに、**ジッター(ばらつき)**を加えます。多くのクライアントが、同じタイミングで再試行すると、相手に、再び負荷が集中するためです。間隔に、ランダムな幅を持たせて、再試行のタイミングを、ずらします。

import random
import time

def wait_time(attempt, base=1.0, cap=30.0):
    # 指数バックオフ:1, 2, 4, 8... 秒(上限 cap)
    delay = min(cap, base * (2 ** attempt))
    # ジッター:0〜delay の間で、ばらつかせる
    return random.uniform(0, delay)

for attempt in range(4):
    # ... リクエストを送り、再試行すべき失敗なら:
    time.sleep(wait_time(attempt))

回数と、全体の時間に、上限を設ける

再試行には、必ず上限を設けます。

相手が長時間不調の場合に、延々と再試行を続けるのは、避けてください。相手の復旧を、かえって妨げることがあります。

二重処理を防ぐ

再試行で、特に注意が必要なのは、決済や登録のように、繰り返すと結果が変わる操作です。タイムアウトした時点では、相手が処理を終えているかもしれません。

そのまま再試行すると、二重に処理されます。防ぐには、冪等キーのような仕組みが必要です(冪等キー(Idempotency-Key)とは、冪等性とは)。

相手を守る:続けて失敗する場合は、止める

相手が、続けて失敗を返している時に、そのまま呼び続けるのは、お互いに良くありません。一定回数、続けて失敗したら、しばらく呼び出しを止める仕組みを入れることがあります。これは、サーキットブレーカーと呼ばれる考え方です(サーキットブレーカーとは)。

AIにコードを書いてもらう時の注意

AIに、APIを呼ぶコードを頼むと、タイムアウトの設定がないコードや、失敗したら、すぐに無限に再試行するコードが、出てくることがあります。依頼する時に、条件を指定してください。

APIを呼ぶコードを書いてください。条件:①接続と応答のタイムアウトを設定する ②再試行するのは、一時的な失敗(通信エラー・429・503)のみ ③再試行は、指数バックオフ+ジッターで、最大3回 ④全体の時間にも上限を設ける ⑤APIキーは環境変数から読む

書かれたコードも、この条件が入っているかを、確認してください(AIが書いたコードをそのまま使ってはいけない理由)。

まとめ

呼び出しの回数の制限については、APIをループで呼ぶ時の3つの約束もご覧ください。

PR

Web APIとシステム連携の入門書を探す

Amazonで見る
SHAREXLINEはてブ

よくある質問

Q.タイムアウトは、何秒に設定すればよいですか?

A.一律の正解はありません。相手のAPIの通常の応答時間と、自分の処理が許容できる待ち時間から決めます。公式に推奨値があれば、それを参考にしてください。短すぎると、正常な処理も失敗扱いになり、長すぎると、障害の時に、自分側が固まってしまいます。

Q.失敗したら、すぐに再試行してよいですか?

A.すぐに再試行すると、相手が不調な時に、さらに負荷をかけてしまいます。間隔をあけ、失敗するたびに間隔を延ばし、回数にも上限を設けてください。また、再試行しても意味のない失敗(認証の誤りなど)は、再試行しません。

Q.再試行で、二重処理にならないか心配です。

A.操作の性質によります。参照のような、繰り返しても結果が変わらない操作は、問題ありません。決済や登録のような操作は、再試行で二重に処理される可能性があるため、冪等キーなどの仕組みで、防ぐ必要があります。

関連記事

プログラミング用語解説

JSONとは?書き方の基本ルールと、よくあるエラーの直し方をやさしく解説

APIや設定ファイルでよく見かけるJSONとは何か。書き方の基本ルール、使えるデータの種類、「カンマ」「引用符」などよくあるエラーの原因まで、初心者向けに解説します。

プログラミング用語解説

ストラングラーパターンとは?古いシステムを止めずに、少しずつ新しくする移行方法

古いシステムを、一度に全部作り直すのは、リスクが大きい方法です。ストラングラーパターンは、入口で振り分けながら、機能ごとに少しずつ新しいシステムへ移していく方法です。仕組み、進め方の5ステップ、向いている場面と、つまずきやすい点を解説します。

プログラミング用語解説

REST APIとGraphQLの違い|メリット・デメリットと選び方

REST APIとGraphQLの違いを、レストランの注文に例えて解説。メリット・デメリットの比較表と、どちらを選ぶかの判断基準もまとめました。

プログラミング用語解説

関数の引数とは?位置引数・キーワード引数・デフォルト値をPythonで解説

引数とは、関数に渡す値のことです。位置引数・キーワード引数・デフォルト値の違い、引数の数が合わない時のエラー、デフォルト値にリストを使ってはいけない理由を、Pythonの短いコードと図解で解説します。

最新のIT関連書籍 トップ10

PR / 楽天市場の売れ筋ランキングを定期的に取得しています。価格は変動する場合があるため、購入前に各ストアでご確認ください。