Terraform 工作流程的關鍵指令 - Init, Plan, Apply

Posted by MingLun Allen Wu on Friday, August 30, 2024

TL;DR

本文探討了 Terraform 的三個關鍵指令:

  • terraform init 用於初始化配置並下載所需的 Provider
  • terraform plan 用於生成將當前狀態轉換為期望狀態的行動方案
  • terraform apply 則負責執行該方案來實現變更。

了解這些指令的作用對於有效管理基礎設施至關重要。


前言

在透過 Terraform 進行 Infrastructure as Code (IaC) 的工作流程中,有幾個關鍵指令。

透過這些指令,我們可以了解 Terraform 與部署目標 (例如雲端服務供應商) 互動的核心機制。

這篇筆記將逐一解析 terraform initterraform planterraform apply 這三個指令的作用,藉此更好地掌握 Terraform 的工作原理,以及如何有效地管理基礎設施配置。


Terraform init

這是執行 Terraform 的初始化階段,執行 terraform init 時,Terraform 將會掃描當前工作目錄下所有的 Configuration (也就是以 .tf 結尾的檔案),將所需的 Provider 下載到當前目錄的 .terraform 資料夾中。

何謂 Terraform Provider ?

Terraform Provider 正是 Terraform 威力強大的秘訣,我們可以將 Provider 想像成外掛式的 Plugin,Terraform 實際上是透過這些 Provider 與部署目標 (例如 GCP, AWS 甚至是 Docker…) 提供的 API 進行互動。

可以在 Terraform Registry 找到不同類型的 Provider

Terraform Provider 下載完成後,Terraform 會在當前目錄建立 .terraform.lock.hcl 檔案來紀錄「所有 Provider 的版本」。

(概念上類似 Python 套件管理器 Poetrypoetry.lock 檔案。)

值得注意的是:在這個階段並不會驗證 Configuration 的語法、邏輯是否正確,只是進行「事前準備」,例如:下載 Provider, Module,以及載入 Backend 的相關設定。


Terraform plan

Terraform plan 的目的是建立一個行動方案,讓部署目標可以由「實際狀態」轉換成「期望狀態」

State File

Terraform 其實不知道在「實際環境」中到底部署了多少元件,而是在部署過程中,透過 State File 來紀錄元件的狀態。

State File 是以 JSON 的格式來儲存每一個元件的型態、屬性、使用的 Provider 等相關資訊,相較於開發者撰寫的 Configuration (.tf 結尾的檔案),State File 中會紀錄更詳細的內容。

這個檔案預設會在工作目錄下,以 terraform.tfstate 的形式存在,但在團隊協作時,通常會將這個檔案放在可共享的協作空間 (例如 GCS),此種配置通常稱為 Remote Backend,由這個共享的檔案來扮演 “Single Source of Truth” 的角色。

建立 Dependency Graph

執行 terraform plan 時,Terraform 會解析 Configuration 的結構,根據每一個元件的 Input / Output 關係,建立起部署元件的相依關係,稱之為 Dependency Graph

要查看 Dependency Graph,我們可以透過 terraform graph 指令來查看。

(Command: terraform graph)

舉例來說,當我們使用 :

terraform graph -type=plan | dot -Tpng >graph.png

可以得到類似下圖的結果:

Dependency Graph

透過圖片能夠掌握當前 Terraform Configuration 定義的元件相依關係。

確認元件是否存在於 State File 中

接下來,Terraform 將會比對 Dependency Graph 中的元件和 State File,目的是要「確認是否有部署過這個元件」。

  • 如果該元件的相關資訊出現在 State File 中 :
    • 代表此元件曾經使用 Terraform 部署過。
    • Terraform 會透過 Provider 來呼叫部署平台的 API,確認該元件的「實際狀態」。
  • 如果該元件的相關資訊沒有出現在 State File 中 :
    • Terraform 將會認為這是一個全新的資源。
    • Terraform 不會透過 Provider 確認元件的狀態。
    • 此元件的 Plan 必定執行成功 (因為並沒有實際確認)。
    • 上述情況反而容易出現錯誤!如果有人以 Terraform 以外的方式部署資源,由於 Plan 時並沒有確認實際狀況,容易在後續執行時,遇到衝突 (例如 Naming conflict)。

產出 Plan File

Terraform 根據上述邏輯確認每一個元件的狀態後,會產生一個 Action Plan,其中針對每一個元件給予幾個不同的行為,包含:

  • Create
  • Update
  • Destroy

Terraform apply

Plan 階段確認完狀態後,透過 terraform apply 指令,將會執行上述提到的 Action Plan。

在執行時,Terraform 將會根據 Dependency Graph 的順序來依序執行,如果某些元件在 Dependency Graph 中沒有相依關係,則 Terraform 將會平行執行這些元件的操作。

執行 Apply 時,Terraform 會不斷透過 Provider 去操作、確認部署目標的狀態,並將結果更新至 State File 中,並將結果輸出至 Output。



See Also