tfactionのセットアップ手順を解説
tfactionとは
TerraformのCI/CDをGitHub Actions上で実行するためのOSSです。
tfaction自体は複数のComposite ActionとJavaScript Actionの集合体になっています。またtfactionのRepositoryから、同開発者のtfcmtやAquaなどを利用しており、これらを組み合わせてTerraformに必要なWorkflowを簡単に作成できるようになっています。
他にもTerraform CloudやAtlantisなど類似ツールはありますが、導入や運用のコストを考えると、非常にオススメしたいツールです。有名な会社も多数利用しています。(参考)
詳細は開発者の鈴木さんの記事も参照ください。
フォルダ構成
完成イメージは以下の構成になります。
.
├── .github
│ └── workflows
│ ├── test.yml
│ ├── plan.yml
│ └── apply.yml
├── environments
│ ├── dev
│ │ ├── .terraform-version
│ │ ├── backend.tf
│ │ ├── locals.tf
│ │ ├── main.tf
│ │ ├── providers.tf
│ │ ├── terraform.tf
│ │ └── tfaction.yaml
│ ├── prd
│ └── .tflint.hcl
├── modules
│ ├── init
│ │ ├── main.tf
│ │ ├── outputs.tf
│ │ ├── variables.tf
│ │ └── tfaction_module.yaml
│ └── .tflint.hcl
├── .trivyignore.yaml
├── tfaction-root.yaml
├── aqua.yaml
└── trivy.yaml
詳細は以下のリポジトリを参照ください。
僕の場合はtfmigrateの設定と、dev環境はTerragruntを使用していたり、その他のworkflowも存在していますが、この記事ではtfactionの導入までとして割愛します。
セットアップの概要
- Repositoryの作成
- GitHub Appの作成とインストール
- GitHub Secretsの登録
- OIDC用のIAM Roleの作成
- S3 Bucketの作成
- tfaction用の設定ファイルの作成
- workflowファイルの作成
セットアップの詳細
1. Repositoryの作成
GitHub ActionsはRepositoryがPublicの場合は無料で利用できますが、Privateでは実行時間に上限が存在するため注意してください。
2. GitHub Appの作成とインストール
tfactionがRepositoryにアクセスするために必要です。
Appの作成方法はGitHubのドキュメントを参照ください。必要な権限はtfactionのドキュメントに記載されています。

Appを作成したら1で作成したRepositoryにインストールします。
インストールが完了するとRopositoryにAppが表示されます。

3. GitHub Secretsの登録
作成したAppはこちらから確認できます。
Appを選択し、GeneralからApp ID、Private keysを取得します。
RepositoryのSettingsを選択し、Repository secretsにそれぞれ登録します。

4. OIDC用のIAM Roleの作成
GitHub ActionsからAWSに安全にアクセスするためには、OIDC(OpenID Connect)を利用したIAM Roleを作成します。アクセスキーを使わずに、Workflow実行時に一時的な認証情報を払い出せます。
tfactionでは4個のRole(terraform plan/apply、tfmigrate plan/apply)を使い分けます。
条件に応じてPolicyは変更してください。今回はシンプルにplanにはReadOnly、applyにはAdmin権限を付けていて、terraformとtfmigrateは共通のRoleを利用しています。
5. S3 Bucketの作成
tfstate、Plan file(現在はGitHub Artifactsに保存されるようになったようです)、tfmigrate historyに使用するBucketです。
それぞれのBucketを作成しても、共通にしてディレクトリで分けても問題ありません。
6. tfaction用の設定ファイルの作成
tfaction-root.yaml
Repositoryのルートディレクトリに作成してください。(.ymlではエラーになったため、.yamlにする必要があるようです)
このファイルでtfactionの全般的な設定をします。
設定値の詳細はtfactionの公式ドキュメントを参照ください。
environments/{env}/tfaction.yaml
各ルートモジュールに作成したら、このファイルを元にtfactionが変更検知をして、CICDのworking directoryに追加します。
tfaction-root.yamlの設定をoverrideできるため、ルートモジュール単位で設定をカスタマイズできます。こちらも詳細は公式ドキュメントを参照ください。
modules/{module}/tfaction_module.yaml
各チャイルドモジュールに作成したら、このファイルを元にtfactionがmoduleを検知します。
こちらも詳細は公式ドキュメントを参照ください。
aqua.yaml
tfactionで必要なCLIツールのバージョン管理をします。
デフォルトでインストールされるツールはtfactionのRepositoryのこちらから確認できます。ここに無い場合はaqua.yamlに指定する必要があります。デフォルトでインストールされるものも、バージョンを記載すればoverrideできます。
.tflint.hcl
tfactionでtflintが使用したい場合に必要です。
ルートモジュール、チャイルドモジュールで設定を分けたい場合はそれぞれに、共通の場合はルートディレクトリに作成してください。僕は分けるバージョンにしています。
trivy.yaml
tfactionでtrivyを使用したい場合に必要です。
.trivyignore.yaml
trivyの検知対象から除外したいものを記載してください。
7. workflowファイルの作成
いつものように、.github/workflows/以下にyamlファイルを作成します。僕の場合はtest、plan、applyに分けました。ここではtfaction固有の設定を記載します。詳細は各ファイルを参照ください。
test.yml
plan.yml
apply.yml
長くなりましたが準備としてはこれで以上です。
動かしてみる
featureブランチからmainブランチへPRを作成します。
ルートモジュールを変更したら、変更したディレクトリのみが対象となり、チャイルドモジュールを変更したら、全てのディレクトリが対象となります。

ちなみにApplyが失敗すると、以下のようなfollow-upのPRを自動作成してくれます。(あくまでPRを作成するだけでソースコードの修正は自分でやる必要があります)

フォーマットを検知したら自動修正のコミットをしてくれます。

PRをマージするとapplyのworkflowが走り、apply結果がコメントされます。

ソースコードの変更無しでもCICDを走らせたい
tfactionはソースコードの変更を検知してCICDの対象としていますが、PRにtarget:{target}(e.g. target:dev)のlabelを付けることで強制的に対象とすることができます。
label名はtfaction-root.yamlで設定可能で、デフォルトはtargetです。{target}の部分はtarget_groupsのtargetで設定可能で、デフォルトはルートモジュールへの相対パスです。
(※labelを付けた後にworkflowのre-runをすることでsetup以降のstepが実行されます)
まとめ
以前までTerraformのCICD構築のために、自分でShellを書いたり、色々なツールを組み合わせて頑張って構築していましたが、tfactionを利用することで、本来のインフラ構築に集中できる環境を高速で構築できます。
各種セキュリティツールも対応していますし、今回紹介できなかった便利なworkflowもあったりするので、もし気になった方はぜひ試して貰えたらと思います。
Discussion
Plan file は S3 ではなく GitHub Artifacts に保存されます。
正しくはこちらですね。
内部的に install という action が実行されてここにあるものがインストールされます。
prefix は
target:ですが、設定可能です。tfaction-root-yaml の
target_groupsでtargetという項目があるのでそこで設定が可能で、デフォルトは Root Module への相対パスになります。コミットが必要とありますが、正確には workflow を re-run するだけでも大丈夫です。
ありがとうございます!記事に反映させていただきました。
ありがとうございます!installのactionがあったんですねmm
こちらも記事に反映させていただきました。
ありがとうございます!こちらも記事に反映させていただきました。