祐成

API 一直掛怎麼辦?三層容錯讓使用者無感

我請 Claude 一段一段教我讀蒸餾精華。第一段講 API 呼叫的三道防線,我一開始以為是「避錯」,結果搞錯了。

朱祐成
· 7 分鐘閱讀 · 學習筆記
API 一直掛怎麼辦?三層容錯讓使用者無感
Image courtesy of The Metropolitan Museum of Art, Open Access

梵谷《麥田與柏樹》(Wheat Field with Cypresses),1889 年。梵谷(Vincent van Gogh)於聖雷米精神療養院期間創作此畫,翻騰的天空、搖曳的麥浪與挺拔的柏樹,以厚重筆觸與旋轉線條交織,展現他對普羅旺斯風景的強烈情感投射。現藏於紐約大都會藝術博物館。

你的程式呼叫外部 API,突然回傳 500 錯誤。使用者只看到一個空白畫面,什麼都做不了。這種事不是偶爾發生,而是遲早會發生——差別只在你有沒有準備好防線。


三層容錯架構

只要你的服務依賴外部 API(抓資料、呼叫 AI、第三方登入),就需要這套防線。核心精神:錯誤一定會來,但使用者不該感受到。

┌─────────────────────────────────────────────┐
│  Tier 1(主要 API)                          │
│  → 4 次重試,指數退避 + 隨機抖動              │
│  → 5xx 才重試,4xx 直接放棄                  │
├─────────────────────────────────────────────┤
│  ↓ 全部失敗                                  │
├─────────────────────────────────────────────┤
│  Tier 2(備用 API)                          │
│  → 同樣 4 次重試                             │
├─────────────────────────────────────────────┤
│  ↓ 全部失敗                                  │
├─────────────────────────────────────────────┤
│  Tier 3(最終 API)                          │
│  → 同樣 4 次重試                             │
├─────────────────────────────────────────────┤
│  每次降級 → 自動發 Webhook 通知               │
└─────────────────────────────────────────────┘

三件事讓這套架構有效:重試(同一個 API 再試幾次)、降級(主要的掛了,自動換備用)、通知(每次降級都告訴你,事後能處理)。


關鍵區分

錯誤類型該怎麼做為什麼
5xx(伺服器掛了)重試通常是暫時的
4xx(請求有問題)直接停重試也沒用

我的追問與發現

「這就是一個好的『避錯』架構吧?」

不是「避錯」,是「容錯」。差一個字,觀念完全不同。避錯是想辦法不讓錯誤發生(幻想),容錯是承認錯誤一定會來,但設計好防線讓使用者感受不到(工程)。

「不打 API 的服務需要這個嗎?」

不需要。純靜態 HTML 頁面沒有外部依賴,完全不需要這套。這個模式只在「你依賴別人的服務」時才有價值。依賴越多、越關鍵,架構就越重要。


你可以怎麼用

  • 盤點你的專案裡有哪些外部 API 呼叫,列出來
  • 最關鍵的那個 API,先加上重試 + 指數退避(不需要三層,一層就有用)
  • 區分 4xx 和 5xx 的處理邏輯,別傻傻全部重試
  • 加一個通知機制(Slack Webhook、Email、LINE Notify 都行),讓降級不是無聲的

延伸連結


一句話帶走

避錯是幻想,容錯是工程——錯誤會來,但使用者不該感受到。



📚 完整學習對話紀錄(想看完整脈絡可展開)

原文(蒸餾精華 第 1 段)

最可靠的 API 呼叫模式:

Tier 1(主要)→ 4 次重試,指數退避 + 隨機抖動
  ↓ 失敗
Tier 2(備用)→ 4 次重試,同上
  ↓ 失敗
Tier 3(最終)→ 4 次重試,同上
  ↓ 每次降級都發 Webhook 通知

關鍵細節:

  • 區分 5xx(可重試)和 4xx(直接放棄)
  • 指數退避 + 隨機抖動避免雷擊效應
  • 每次降級自動通知(Google Chat Webhook)

Claude 的白話解釋

你呼叫外部 API 時,不要只試一次就放棄。這個模式設計了三道防線:

主要 API → 試 4 次失敗 → 換備用 API → 再試 4 次失敗 → 換最終 API → 再試 4 次

每次重試之間的等待時間會越來越長(指數退避),而且加一點隨機秒數(抖動),避免一堆使用者同時重試把伺服器打爆(雷擊效應)。

為什麼好?

  • 4xx 錯誤(你的請求有問題)→ 直接停,不浪費時間重試
  • 5xx 錯誤(伺服器掛了)→ 值得重試,可能只是暫時的
  • 每次降級都自動發 Webhook 通知 → 你不在電腦前也知道出事了

實際應用:任何你寫的程式只要會打外部 API(抓網頁、呼叫 AI 服務、短網址跳轉預覽),都應該套這個模式。


我的提問:這就是一個好的「避錯」架構吧?

讀完之後我的直覺是:情境發生在當服務有呼叫 API 的時候,這就是一個好的避錯架構,對吧?


Claude 的修正:不是「避錯」,是「容錯」

更精確地說:不是「避錯」,是「容錯」。

錯誤一定會發生(網路斷、伺服器掛、API 限流),你避不掉。這個架構的精神是:

錯誤會來,但使用者不該感受到。

它做了三件事:

  1. 重試 — 同一個 API 再試幾次(因為很多 5xx 是暫時的)
  2. 降級 — 主要的真的掛了,自動換備用的頂上
  3. 通知 — 每次降級都告訴你,讓你事後能處理

如果你的服務不呼叫外部 API(比如純靜態 HTML 頁面),就完全不需要這個。這個模式只在「你依賴別人的服務」時才有價值。

依賴越多、越關鍵,這個架構就越重要。


我學到的

「避錯」跟「容錯」差一個字,觀念完全不同。避錯是想辦法不讓錯誤發生,容錯是承認錯誤一定會來,但設計好防線讓使用者感受不到。前者是幻想,後者是工程。