<?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>Serverless 部署 CI/CD on Tarragon</title><link>https://tarrragon.github.io/blog/ci/serverless-deploy/</link><description>Recent content in Serverless 部署 CI/CD on Tarragon</description><generator>Hugo -- gohugo.io</generator><language>zh-TW</language><copyright>Tarragon (CC BY 4.0)</copyright><lastBuildDate>Wed, 06 May 2026 00:00:00 +0000</lastBuildDate><atom:link href="https://tarrragon.github.io/blog/ci/serverless-deploy/index.xml" rel="self" type="application/rss+xml"/><item><title>Serverless function 版本、事件來源與回復流程</title><link>https://tarrragon.github.io/blog/ci/serverless-deploy/function-version-event-flow/</link><pubDate>Thu, 21 May 2026 00:00:00 +0000</pubDate><guid>https://tarrragon.github.io/blog/ci/serverless-deploy/function-version-event-flow/</guid><description>&lt;p>Serverless 發布流程的核心責任是把函式 artifact、&lt;a href="https://tarrragon.github.io/blog/ci/knowledge-cards/function-alias/" data-link-title="Function Alias" data-link-desc="說明 serverless function alias 如何把穩定入口指向特定版本並支援流量切換與回復">Function Alias&lt;/a>、權限與 &lt;a href="https://tarrragon.github.io/blog/ci/knowledge-cards/event-source/" data-link-title="Event Source" data-link-desc="說明 serverless 與事件驅動流程中觸發來源如何影響 retry、dead-letter 與回復策略">Event Source&lt;/a> 一起推進。Serverless 部署看起來比長駐服務短，但每次 invocation 都依賴 runtime、IAM、event source、retry policy 與 observability；CI/CD 需要把這些條件視為發布契約。&lt;/p>
&lt;h2 id="流程定位">流程定位&lt;/h2>
&lt;p>Serverless 的風險集中在觸發條件。函式部署成功只代表新版本存在，實際風險會在 HTTP request、queue message、topic event、scheduled job 或 edge request 觸發時出現。發布流程要能區分「版本建立成功」「alias 切流量成功」「事件來源行為正確」三件事。&lt;/p>
&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>Package&lt;/td>
 &lt;td>產生 function bundle / layer&lt;/td>
 &lt;td>dependency、runtime target 是否固定&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>Version&lt;/td>
 &lt;td>發布 immutable function version&lt;/td>
 &lt;td>version 是否可追到 commit&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>Alias / traffic&lt;/td>
 &lt;td>控制新舊版本流量&lt;/td>
 &lt;td>alias 權重、錯誤率、冷啟動&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>Permission&lt;/td>
 &lt;td>限制 IAM、secret、resource policy&lt;/td>
 &lt;td>最小權限與環境隔離&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>&lt;a href="https://tarrragon.github.io/blog/ci/knowledge-cards/event-source/" data-link-title="Event Source" data-link-desc="說明 serverless 與事件驅動流程中觸發來源如何影響 retry、dead-letter 與回復策略">Event Source&lt;/a>&lt;/td>
 &lt;td>管理 trigger、retry、dead-letter&lt;/td>
 &lt;td>重試與毒訊息處理是否明確&lt;/td>
 &lt;/tr>
 &lt;tr>
 &lt;td>Recovery&lt;/td>
 &lt;td>alias rollback、disable trigger、replay&lt;/td>
 &lt;td>是否能止血與修補資料&lt;/td>
 &lt;/tr>
 &lt;/tbody>
&lt;/table>
&lt;p>Package 階段負責產生可執行 bundle。Serverless 常見失敗是本機 dependency 可用，但打包後缺檔、runtime target 不符、native extension 不相容或 layer 版本漂移；CI 應在接近目標 runtime 的環境做 smoke test。&lt;/p>
&lt;p>Version 階段負責建立不可變版本。直接覆蓋 &lt;code>$LATEST&lt;/code> 會讓事故追溯困難；正式流量應指向 version 或 &lt;a href="https://tarrragon.github.io/blog/ci/knowledge-cards/function-alias/" data-link-title="Function Alias" data-link-desc="說明 serverless function alias 如何把穩定入口指向特定版本並支援流量切換與回復">Function Alias&lt;/a>，讓 rollback 能把 alias 切回前一個已知版本。&lt;/p>
&lt;p>&lt;a href="https://tarrragon.github.io/blog/ci/knowledge-cards/function-alias/" data-link-title="Function Alias" data-link-desc="說明 serverless function alias 如何把穩定入口指向特定版本並支援流量切換與回復">Function Alias&lt;/a> / traffic 階段負責控制流量切換。HTTP function 可以用少量權重 canary；queue trigger 則要觀察 batch failure、retry、dead-letter 與 downstream side effect，因為同一個錯誤 event 可能被重試多次。&lt;/p>
&lt;p>Permission 階段負責限制 blast radius。Serverless 函式容易因部署方便而累積過大 IAM 權限；每個 function 應只拿到必要 resource、secret 與 network access，並把 production secret 與 preview / staging 隔離。&lt;/p>
&lt;p>&lt;a href="https://tarrragon.github.io/blog/ci/knowledge-cards/event-source/" data-link-title="Event Source" data-link-desc="說明 serverless 與事件驅動流程中觸發來源如何影響 retry、dead-letter 與回復策略">Event Source&lt;/a> 階段負責定義失敗重送語意。Queue、topic、object storage、HTTP 與 scheduler 的錯誤行為不同；CI/CD 文件要記錄 retry 次數、dead-letter destination、batch size、concurrency limit 與 replay 條件。&lt;/p>
&lt;p>Recovery 階段負責止血。Serverless 常見止血方式是 alias rollback、停用 trigger、降低 concurrency、清理毒訊息、重放事件或 forward fix；只回退 code 版本不一定能處理已經排入 queue 的事件。&lt;/p></description><content:encoded><![CDATA[<p>Serverless 發布流程的核心責任是把函式 artifact、<a href="/blog/ci/knowledge-cards/function-alias/" data-link-title="Function Alias" data-link-desc="說明 serverless function alias 如何把穩定入口指向特定版本並支援流量切換與回復">Function Alias</a>、權限與 <a href="/blog/ci/knowledge-cards/event-source/" data-link-title="Event Source" data-link-desc="說明 serverless 與事件驅動流程中觸發來源如何影響 retry、dead-letter 與回復策略">Event Source</a> 一起推進。Serverless 部署看起來比長駐服務短，但每次 invocation 都依賴 runtime、IAM、event source、retry policy 與 observability；CI/CD 需要把這些條件視為發布契約。</p>
<h2 id="流程定位">流程定位</h2>
<p>Serverless 的風險集中在觸發條件。函式部署成功只代表新版本存在，實際風險會在 HTTP request、queue message、topic event、scheduled job 或 edge request 觸發時出現。發布流程要能區分「版本建立成功」「alias 切流量成功」「事件來源行為正確」三件事。</p>
<table>
  <thead>
      <tr>
          <th>階段</th>
          <th>責任</th>
          <th>判讀訊號</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td>Package</td>
          <td>產生 function bundle / layer</td>
          <td>dependency、runtime target 是否固定</td>
      </tr>
      <tr>
          <td>Version</td>
          <td>發布 immutable function version</td>
          <td>version 是否可追到 commit</td>
      </tr>
      <tr>
          <td>Alias / traffic</td>
          <td>控制新舊版本流量</td>
          <td>alias 權重、錯誤率、冷啟動</td>
      </tr>
      <tr>
          <td>Permission</td>
          <td>限制 IAM、secret、resource policy</td>
          <td>最小權限與環境隔離</td>
      </tr>
      <tr>
          <td><a href="/blog/ci/knowledge-cards/event-source/" data-link-title="Event Source" data-link-desc="說明 serverless 與事件驅動流程中觸發來源如何影響 retry、dead-letter 與回復策略">Event Source</a></td>
          <td>管理 trigger、retry、dead-letter</td>
          <td>重試與毒訊息處理是否明確</td>
      </tr>
      <tr>
          <td>Recovery</td>
          <td>alias rollback、disable trigger、replay</td>
          <td>是否能止血與修補資料</td>
      </tr>
  </tbody>
</table>
<p>Package 階段負責產生可執行 bundle。Serverless 常見失敗是本機 dependency 可用，但打包後缺檔、runtime target 不符、native extension 不相容或 layer 版本漂移；CI 應在接近目標 runtime 的環境做 smoke test。</p>
<p>Version 階段負責建立不可變版本。直接覆蓋 <code>$LATEST</code> 會讓事故追溯困難；正式流量應指向 version 或 <a href="/blog/ci/knowledge-cards/function-alias/" data-link-title="Function Alias" data-link-desc="說明 serverless function alias 如何把穩定入口指向特定版本並支援流量切換與回復">Function Alias</a>，讓 rollback 能把 alias 切回前一個已知版本。</p>
<p><a href="/blog/ci/knowledge-cards/function-alias/" data-link-title="Function Alias" data-link-desc="說明 serverless function alias 如何把穩定入口指向特定版本並支援流量切換與回復">Function Alias</a> / traffic 階段負責控制流量切換。HTTP function 可以用少量權重 canary；queue trigger 則要觀察 batch failure、retry、dead-letter 與 downstream side effect，因為同一個錯誤 event 可能被重試多次。</p>
<p>Permission 階段負責限制 blast radius。Serverless 函式容易因部署方便而累積過大 IAM 權限；每個 function 應只拿到必要 resource、secret 與 network access，並把 production secret 與 preview / staging 隔離。</p>
<p><a href="/blog/ci/knowledge-cards/event-source/" data-link-title="Event Source" data-link-desc="說明 serverless 與事件驅動流程中觸發來源如何影響 retry、dead-letter 與回復策略">Event Source</a> 階段負責定義失敗重送語意。Queue、topic、object storage、HTTP 與 scheduler 的錯誤行為不同；CI/CD 文件要記錄 retry 次數、dead-letter destination、batch size、concurrency limit 與 replay 條件。</p>
<p>Recovery 階段負責止血。Serverless 常見止血方式是 alias rollback、停用 trigger、降低 concurrency、清理毒訊息、重放事件或 forward fix；只回退 code 版本不一定能處理已經排入 queue 的事件。</p>
<h2 id="事件來源判讀">事件來源判讀</h2>
<p>事件來源判讀的責任是找出失敗是否可重試。Serverless 常被誤判為「函式自己失敗」，但實際根因可能是 event schema、權限、上游重試或下游限流。</p>
<table>
  <thead>
      <tr>
          <th>Event source</th>
          <th>常見失敗</th>
          <th>下一步</th>
      </tr>
  </thead>
  <tbody>
      <tr>
          <td>HTTP / API</td>
          <td>status code、timeout、冷啟動</td>
          <td>看 latency、concurrency、alias</td>
      </tr>
      <tr>
          <td>Queue</td>
          <td>batch failure、毒訊息、重試風暴</td>
          <td>看 DLQ、batch size、visibility timeout</td>
      </tr>
      <tr>
          <td>Topic</td>
          <td>event schema 漂移</td>
          <td>驗證 publisher / subscriber 契約</td>
      </tr>
      <tr>
          <td>Object store</td>
          <td>權限或路徑 pattern 錯誤</td>
          <td>檢查 resource policy 與 filter</td>
      </tr>
      <tr>
          <td>Scheduler</td>
          <td>timezone、重入、上次執行未完成</td>
          <td>檢查 idempotency 與 lock</td>
      </tr>
  </tbody>
</table>
<p>這張表讓 release failure 能被導向正確 owner。若 event schema 變了，修 function 可能只是表面補丁；真正的 gate 要加在 publisher contract 或 sample event validation。</p>
<h2 id="最小發布-gate">最小發布 gate</h2>
<p>Serverless workflow 的最小 gate 應覆蓋 package、permission、event 與 alias。缺其中一段，部署成功就可能只是建立了一個尚未被驗證的函式版本。</p>
<ol>
<li>Package bundle，固定 runtime target 與 dependency。</li>
<li>對 bundle 執行 unit / contract / sample event test。</li>
<li>用 least privilege policy 做 deploy dry run 或 policy diff。</li>
<li>發布 immutable function version。</li>
<li>用 alias 將少量流量導向新版本。</li>
<li>觀察 error、latency、retry、DLQ 與 downstream 指標。</li>
<li>指標穩定後提高 alias 權重或完成切換。</li>
<li>指標觸發 tripwire 時切回 alias、停用 trigger 或啟動 repair。</li>
</ol>
<p>這個流程把 Serverless 發布從「上傳函式」提升成可回復流程。對事件驅動函式而言，trigger 與 retry policy 是發布契約的一部分。</p>
<h2 id="下一步路由">下一步路由</h2>
<ul>
<li>Serverless 部署總覽：回 <a href="../">Serverless 部署 CI/CD</a>。</li>
<li>Rollout 概念：讀 <a href="/blog/ci/knowledge-cards/rollout-strategy/" data-link-title="Rollout Strategy" data-link-desc="說明新版本如何以可控節奏推進到全部流量">Rollout Strategy</a>。</li>
<li>失敗處理：讀 <a href="../../github-actions-failure-flow/">CI 失敗到修復發布流程</a>。</li>
</ul>
]]></content:encoded></item></channel></rss>