<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/"><channel><title>Circuit-Breaker on Tarragon</title><link>https://tarrragon.github.io/blog/tags/circuit-breaker/</link><description>Recent content in Circuit-Breaker on Tarragon</description><generator>Hugo -- gohugo.io</generator><language>zh-TW</language><copyright>Tarragon (CC BY 4.0)</copyright><lastBuildDate>Sat, 20 Jun 2026 00:00:00 +0000</lastBuildDate><atom:link href="https://tarrragon.github.io/blog/tags/circuit-breaker/index.xml" rel="self" type="application/rss+xml"/><item><title>熔斷器</title><link>https://tarrragon.github.io/blog/devops/03-traffic-management/circuit-breaker/</link><pubDate>Sat, 20 Jun 2026 00:00:00 +0000</pubDate><guid>https://tarrragon.github.io/blog/devops/03-traffic-management/circuit-breaker/</guid><description>&lt;p>熔斷器保護的是「呼叫外部依賴」的路徑。當外部依賴（資料庫、第三方 API、通知服務）持續失敗時，熔斷器讓後續的呼叫立即失敗（回傳預設值或錯誤），而非每次都等待逾時。等待逾時的代價是佔住 goroutine / thread 不釋放，積累到一定數量就拖垮整個服務。&lt;/p>
&lt;h2 id="三狀態模型">三狀態模型&lt;/h2>
&lt;h3 id="closed正常">Closed（正常）&lt;/h3>
&lt;p>所有呼叫正常通過。熔斷器記錄成功和失敗的計數。&lt;/p>
&lt;h3 id="open熔斷">Open（熔斷）&lt;/h3>
&lt;p>當失敗率或連續失敗次數超過閾值時，熔斷器進入 open 狀態。此後所有呼叫&lt;strong>立即回傳錯誤&lt;/strong>，不實際呼叫外部依賴。&lt;/p>
&lt;p>Open 狀態持續固定時間（如 30 秒），時間到後進入 half-open。&lt;/p>
&lt;h3 id="half-open探測">Half-open（探測）&lt;/h3>
&lt;p>允許少量呼叫（如 1 個）實際通過到外部依賴。如果成功 → 回到 closed；如果失敗 → 回到 open（重設計時器）。&lt;/p>
&lt;p>Half-open 的目的是自動探測依賴是否恢復，不需要人工介入。&lt;/p>
&lt;h2 id="熔斷判斷條件">熔斷判斷條件&lt;/h2>
&lt;table>
 &lt;thead>
 &lt;tr>
 &lt;th>條件&lt;/th>
 &lt;th>適用場景&lt;/th>
 &lt;th>參數&lt;/th>
 &lt;/tr>
 &lt;/thead>
 &lt;tbody>
 &lt;tr>
 &lt;td>連續 N 次失敗&lt;/td>
 &lt;td>依賴完全不可用&lt;/td>
 &lt;td>N = 5-10&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>失敗率 &amp;gt; X%&lt;/td>
 &lt;td>依賴間歇性失敗&lt;/td>
 &lt;td>X = 50%，統計窗口 = 10 秒&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>平均延遲 &amp;gt; Y ms&lt;/td>
 &lt;td>依賴變慢但未失敗&lt;/td>
 &lt;td>Y = 依據 SLA 設定&lt;/td>
 &lt;/tr>
 &lt;/tbody>
&lt;/table>
&lt;p>「失敗」的定義需要明確：HTTP 5xx 是失敗、4xx 通常不是（client 的問題）、timeout 是失敗、connection refused 是失敗。&lt;/p>
&lt;h2 id="熔斷時的-fallback">熔斷時的 fallback&lt;/h2>
&lt;p>熔斷觸發後，呼叫端收到的是「快速失敗」而非逾時。呼叫端需要有 fallback 策略：&lt;/p>
&lt;table>
 &lt;thead>
 &lt;tr>
 &lt;th>依賴&lt;/th>
 &lt;th>Fallback&lt;/th>
 &lt;/tr>
 &lt;/thead>
 &lt;tbody>
 &lt;tr>
 &lt;td>通知服務（Slack webhook）&lt;/td>
 &lt;td>記錄到本地 log、恢復後補發&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>外部 API（enrichment）&lt;/td>
 &lt;td>回傳無 enrichment 的原始資料&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>認證服務&lt;/td>
 &lt;td>用本地 cache 的 token 驗證（短暫降級）&lt;/td>
 &lt;/tr>
 &lt;/tbody>
&lt;/table>
&lt;p>沒有 fallback 的依賴被熔斷 = 對應功能完全不可用。熔斷器保護的是「不讓不可用的功能拖垮整個服務」。&lt;/p>
&lt;h2 id="監控系統的應用">監控系統的應用&lt;/h2>
&lt;p>&lt;a href="https://tarrragon.github.io/blog/monitoring/04-collector/" data-link-title="模組四：Collector 設計" data-link-desc="收 → 驗 → 存 → 查 → 觸發的完整鏈路 — Go 單一 binary、可插拔 Storage Backend、rule engine">Collector&lt;/a> 的 rule engine 在規則命中時可能呼叫外部服務（Slack webhook、HTTP POST 到 alert endpoint）。如果外部服務掛了，每個命中的規則都會等待逾時 — 大量規則命中時 goroutine 積壓。&lt;/p>
&lt;p>熔斷器包在 rule engine 的「執行外部動作」環節：連續 5 次外部呼叫失敗 → 熔斷 → 後續規則命中不再嘗試外部呼叫、改寫本地 log → 30 秒後探測一次 → 外部服務恢復 → 恢復正常呼叫。&lt;/p>
&lt;h2 id="下一步路由">下一步路由&lt;/h2>
&lt;ul>
&lt;li>被動的流量控制 → &lt;a href="https://tarrragon.github.io/blog/devops/03-traffic-management/backpressure/" data-link-title="背壓機制" data-link-desc="下游處理慢時上游怎麼減速 — 有限 buffer &amp;#43; 回壓訊號的設計、和 rate limit 的區別">背壓機制&lt;/a>&lt;/li>
&lt;li>主動的速率限制 → &lt;a href="https://tarrragon.github.io/blog/devops/03-traffic-management/rate-limiting/" data-link-title="Rate Limiting" data-link-desc="主動限制每個來源的請求速率 — per-client vs global、token bucket vs sliding window、優先級豁免">Rate Limiting&lt;/a>&lt;/li>
&lt;li>不同工作負載的資源隔離 → &lt;a href="https://tarrragon.github.io/blog/devops/03-traffic-management/bulkhead/" data-link-title="Bulkhead 隔離" data-link-desc="不同工作負載的資源池隔離 — 一個功能過載不拖垮其他功能的隔艙設計">Bulkhead 隔離&lt;/a>&lt;/li>
&lt;/ul></description><content:encoded><![CDATA[<p>熔斷器保護的是「呼叫外部依賴」的路徑。當外部依賴（資料庫、第三方 API、通知服務）持續失敗時，熔斷器讓後續的呼叫立即失敗（回傳預設值或錯誤），而非每次都等待逾時。等待逾時的代價是佔住 goroutine / thread 不釋放，積累到一定數量就拖垮整個服務。</p>
<h2 id="三狀態模型">三狀態模型</h2>
<h3 id="closed正常">Closed（正常）</h3>
<p>所有呼叫正常通過。熔斷器記錄成功和失敗的計數。</p>
<h3 id="open熔斷">Open（熔斷）</h3>
<p>當失敗率或連續失敗次數超過閾值時，熔斷器進入 open 狀態。此後所有呼叫<strong>立即回傳錯誤</strong>，不實際呼叫外部依賴。</p>
<p>Open 狀態持續固定時間（如 30 秒），時間到後進入 half-open。</p>
<h3 id="half-open探測">Half-open（探測）</h3>
<p>允許少量呼叫（如 1 個）實際通過到外部依賴。如果成功 → 回到 closed；如果失敗 → 回到 open（重設計時器）。</p>
<p>Half-open 的目的是自動探測依賴是否恢復，不需要人工介入。</p>
<h2 id="熔斷判斷條件">熔斷判斷條件</h2>
<table>
  <thead>
      <tr>
          <th>條件</th>
          <th>適用場景</th>
          <th>參數</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td>連續 N 次失敗</td>
          <td>依賴完全不可用</td>
          <td>N = 5-10</td>
      </tr>
      <tr>
          <td>失敗率 &gt; X%</td>
          <td>依賴間歇性失敗</td>
          <td>X = 50%，統計窗口 = 10 秒</td>
      </tr>
      <tr>
          <td>平均延遲 &gt; Y ms</td>
          <td>依賴變慢但未失敗</td>
          <td>Y = 依據 SLA 設定</td>
      </tr>
  </tbody>
</table>
<p>「失敗」的定義需要明確：HTTP 5xx 是失敗、4xx 通常不是（client 的問題）、timeout 是失敗、connection refused 是失敗。</p>
<h2 id="熔斷時的-fallback">熔斷時的 fallback</h2>
<p>熔斷觸發後，呼叫端收到的是「快速失敗」而非逾時。呼叫端需要有 fallback 策略：</p>
<table>
  <thead>
      <tr>
          <th>依賴</th>
          <th>Fallback</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td>通知服務（Slack webhook）</td>
          <td>記錄到本地 log、恢復後補發</td>
      </tr>
      <tr>
          <td>外部 API（enrichment）</td>
          <td>回傳無 enrichment 的原始資料</td>
      </tr>
      <tr>
          <td>認證服務</td>
          <td>用本地 cache 的 token 驗證（短暫降級）</td>
      </tr>
  </tbody>
</table>
<p>沒有 fallback 的依賴被熔斷 = 對應功能完全不可用。熔斷器保護的是「不讓不可用的功能拖垮整個服務」。</p>
<h2 id="監控系統的應用">監控系統的應用</h2>
<p><a href="/blog/monitoring/04-collector/" data-link-title="模組四：Collector 設計" data-link-desc="收 → 驗 → 存 → 查 → 觸發的完整鏈路 — Go 單一 binary、可插拔 Storage Backend、rule engine">Collector</a> 的 rule engine 在規則命中時可能呼叫外部服務（Slack webhook、HTTP POST 到 alert endpoint）。如果外部服務掛了，每個命中的規則都會等待逾時 — 大量規則命中時 goroutine 積壓。</p>
<p>熔斷器包在 rule engine 的「執行外部動作」環節：連續 5 次外部呼叫失敗 → 熔斷 → 後續規則命中不再嘗試外部呼叫、改寫本地 log → 30 秒後探測一次 → 外部服務恢復 → 恢復正常呼叫。</p>
<h2 id="下一步路由">下一步路由</h2>
<ul>
<li>被動的流量控制 → <a href="/blog/devops/03-traffic-management/backpressure/" data-link-title="背壓機制" data-link-desc="下游處理慢時上游怎麼減速 — 有限 buffer &#43; 回壓訊號的設計、和 rate limit 的區別">背壓機制</a></li>
<li>主動的速率限制 → <a href="/blog/devops/03-traffic-management/rate-limiting/" data-link-title="Rate Limiting" data-link-desc="主動限制每個來源的請求速率 — per-client vs global、token bucket vs sliding window、優先級豁免">Rate Limiting</a></li>
<li>不同工作負載的資源隔離 → <a href="/blog/devops/03-traffic-management/bulkhead/" data-link-title="Bulkhead 隔離" data-link-desc="不同工作負載的資源池隔離 — 一個功能過載不拖垮其他功能的隔艙設計">Bulkhead 隔離</a></li>
</ul>
]]></content:encoded></item><item><title>模組三：流量管控</title><link>https://tarrragon.github.io/blog/devops/03-traffic-management/</link><pubDate>Sat, 20 Jun 2026 00:00:00 +0000</pubDate><guid>https://tarrragon.github.io/blog/devops/03-traffic-management/</guid><description>&lt;p>回答「收到的流量超過處理能力時怎麼辦」。四種防護機制各自處理不同層面的過載問題。&lt;/p>
&lt;h2 id="待寫章節">待寫章節&lt;/h2>
&lt;ul>
&lt;li>&lt;input checked="" disabled="" type="checkbox"> 背壓機制（下游慢時上游怎麼減速）&lt;/li>
&lt;li>&lt;input checked="" disabled="" type="checkbox"> Rate Limiting（主動限制每個來源的請求速率）&lt;/li>
&lt;li>&lt;input checked="" disabled="" type="checkbox"> 熔斷器（依賴服務失敗時怎麼快速失敗而非拖慢自己）&lt;/li>
&lt;li>&lt;input checked="" disabled="" type="checkbox"> Bulkhead 隔離（不同工作負載的資源池隔離）&lt;/li>
&lt;/ul>
&lt;h2 id="跨分類引用">跨分類引用&lt;/h2>
&lt;ul>
&lt;li>→ &lt;a href="https://tarrragon.github.io/blog/monitoring/04-collector/" data-link-title="模組四：Collector 設計" data-link-desc="收 → 驗 → 存 → 查 → 觸發的完整鏈路 — Go 單一 binary、可插拔 Storage Backend、rule engine">monitoring 模組四 Collector&lt;/a>：Collector 的 ingestion 防護是本模組的應用場景&lt;/li>
&lt;li>→ &lt;a href="https://tarrragon.github.io/blog/devops/07-burst-traffic/" data-link-title="模組七：突發流量應對" data-link-desc="行銷活動或新聞曝光帶來 10x-100x 流量時怎麼撐 — 突發分類、降級策略、queue 緩衝、規模分級應對">devops 模組七 突發流量&lt;/a>：突發流量時這四種機制怎麼組合使用&lt;/li>
&lt;li>→ &lt;a href="https://tarrragon.github.io/blog/backend/06-reliability/" data-link-title="模組六：可靠性驗證流程" data-link-desc="用 SRE 領域詞彙建問題節點、以服務級案例庫累積驗證脈絡，先建概念與案例庫再進實作交接">backend 可靠性&lt;/a>：熔斷和 bulkhead 也是 backend 的可靠性設計元件&lt;/li>
&lt;/ul></description><content:encoded><![CDATA[<p>回答「收到的流量超過處理能力時怎麼辦」。四種防護機制各自處理不同層面的過載問題。</p>
<h2 id="待寫章節">待寫章節</h2>
<ul>
<li><input checked="" disabled="" type="checkbox"> 背壓機制（下游慢時上游怎麼減速）</li>
<li><input checked="" disabled="" type="checkbox"> Rate Limiting（主動限制每個來源的請求速率）</li>
<li><input checked="" disabled="" type="checkbox"> 熔斷器（依賴服務失敗時怎麼快速失敗而非拖慢自己）</li>
<li><input checked="" disabled="" type="checkbox"> Bulkhead 隔離（不同工作負載的資源池隔離）</li>
</ul>
<h2 id="跨分類引用">跨分類引用</h2>
<ul>
<li>→ <a href="/blog/monitoring/04-collector/" data-link-title="模組四：Collector 設計" data-link-desc="收 → 驗 → 存 → 查 → 觸發的完整鏈路 — Go 單一 binary、可插拔 Storage Backend、rule engine">monitoring 模組四 Collector</a>：Collector 的 ingestion 防護是本模組的應用場景</li>
<li>→ <a href="/blog/devops/07-burst-traffic/" data-link-title="模組七：突發流量應對" data-link-desc="行銷活動或新聞曝光帶來 10x-100x 流量時怎麼撐 — 突發分類、降級策略、queue 緩衝、規模分級應對">devops 模組七 突發流量</a>：突發流量時這四種機制怎麼組合使用</li>
<li>→ <a href="/blog/backend/06-reliability/" data-link-title="模組六：可靠性驗證流程" data-link-desc="用 SRE 領域詞彙建問題節點、以服務級案例庫累積驗證脈絡，先建概念與案例庫再進實作交接">backend 可靠性</a>：熔斷和 bulkhead 也是 backend 的可靠性設計元件</li>
</ul>
]]></content:encoded></item></channel></rss>