はじめに
AI エージェントによるコーディングが普及している今、静的解析・自動テスト・CI/CD の重要性は一層増しています。AI が大量にコードを生成するほど人間のレビューはボトルネックになりやすく、自動で検証しフィードバックする仕組みが不可欠です。
この記事では、Terraform の品質を支える静的解析・自動テスト・CI/CD の構成例を紹介します。実際にこの構成を適用した検証プロジェクトは以下のリポジトリで公開しています。
利用ツール一覧
検証プロジェクトで利用したツールは以下のとおりです。
| ツール | 役割 |
|---|---|
| terraform fmt | コードのフォーマットチェック、自動整形 |
| terraform validate | コードの構文・整合性チェック |
| TFLint | 未使用変数の検出、プロバイダ固有ルールやカスタムルールに基づくLintチェック |
| Checkov | 静的セキュリティ解析およびポリシー準拠チェック |
| terraform test | 自動テスト |
| pre-commit | コミット前の自動検証 |
| GitHub Actions | PR(pull request)作成時や push 時の自動検証 |
構成の全体像
本記事で紹介する構成は、以下の 4 つのパートからなります。
1. ローカル開発時 — terraform test によるテスト実行
2. コミット時(pre-commit) — terraform fmt / tflint / checkov などの高速な自動検証
3. PR 作成時(GitHub Actions) — 静的解析・テストの実行と結果の PR への出力
4. デプロイ時(CI/CD パイプライン) — terraform plan による変更内容の最終確認
ローカル開発時は自動テストでロジックを適宜検証し、コミット時にフォーマットやセキュリティなどを自動チェックします。PR 作成時にはコミット時の静的解析に加えてテストを実行し、問題のあるコードがマージされるのを防ぎます。デプロイ時には terraform plan で実際の変更内容を最終確認し、意図しない変更が適用されるのを防ぎます。
1. ローカル開発時
ローカル開発では、terraform init -backend=false でプロバイダーやモジュールをダウンロードし、terraform test でテストを実行します。terraform test は pre-commit でコミットのたびに実行するのではなく、モジュールの実装や修正のタイミングに応じて実行します。
-
terraform init -backend=false: バックエンドの初期化をスキップして、プロバイダーやモジュールをダウンロードする -
terraform test: .tftest.hcl に定義されたテストを実行する
terraform test の検証内容について
検証プロジェクトでは、モックを用いたテストを実行しています。モックを使っているため、実際に AWS 上へリソースを作成したり、API を呼び出したりすることはありません。そのため、AWS 認証情報がなくても実行できます。
ただし、モックを使う場合は実際の AWS API レスポンスとの乖離が生じる可能性があります。モックテストはロジックの検証には有効ですが、実環境での挙動の確認は別途行うことを推奨します。
テストファイルは役割ごとに次の 2 つに分けています。
- tests/main.tftest.hcl: 指定した変数に応じて、必要なリソースが正しく定義されることを検証
- tests/var_validation.tftest.hcl: 変数のバリデーションが想定どおりにエラーを出すことを検証
Makefile について
よく使うコマンドのセットは Makefile にまとめておくと便利です。検証プロジェクトでは次のように Makefile を定義しています。
.PHONY: init fmt fmt-diff validate test tflint checkov ci
ci: fmt validate test tflint checkov
init:
terraform init -backend=false
fmt:
terraform fmt -recursive -diff
validate: init
terraform validate
test: init
terraform test
tflint:
tflint --init && tflint --recursive
checkov:
checkov -d .
下記のように短縮コマンドで実行することができます。
| Command | Description |
|---|---|
make init |
terraform init -backend=false を実行 |
make fmt |
terraform fmt -recursive -diff を実行 |
make validate |
make init 後に terraform validate を実行 |
make test |
make init 後に terraform test を実行 |
make tflint |
tflint --init && tflint --recursive を実行 |
make checkov |
checkov -d . を実行 |
make ci |
すべてのチェックを実行(fmt / validate / test / tflint / checkov) |
2. コミット時(pre-commit)
pre-commit では、主に下記のツールを実行します。コミットのたびに実行されるため、terraform test は含めず、高速に完了するチェックに絞っています。
- terraform fmt
- terraform validate
- TFLint
- Checkov
terraform validate や Checkov はフォーマッター/リンターに比べて実行時間が長く、開発のテンポが悪くなる場合があります。実行時間が気になり始めたら、pre-commit から外して CI に寄せることも検討してください。
検証プロジェクトの .pre-commit-config.yaml の全容は以下の通りです。
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v6.0.0
hooks:
- id: check-merge-conflict # コンフリクトが生じていないか確認
- id: end-of-file-fixer # ファイル末尾に改行を追加
- id: trailing-whitespace # 行末の余分な空白を削除
- id: mixed-line-ending # 改行コードの混在を防ぐ
- repo: https://github.com/antonbabenko/pre-commit-terraform
rev: v1.105.0
hooks:
- id: terraform_fmt
- id: terraform_validate
- id: terraform_tflint
- id: terraform_docs # ドキュメントを自動生成
- id: terraform_checkov
TFLint について
TFLint には次のような機能があります。
- 主要クラウドプロバイダー(AWS/Azure/GCP)における潜在的なエラー(無効なインスタンスタイプなど)を検出する
- 非推奨の構文や未使用の宣言について警告する
- ベストプラクティスと命名規則を徹底する
設定ファイル .tflint.hcl の全容は下記をご覧ください。検証内容をコメントしています。
Checkov について
Checkov は Terraform などの IaC テンプレートをスキャンし、クラウドインフラストラクチャにおけるセキュリティベストプラクティスやポリシー違反を検出します。
設定ファイル .checkov.yaml の全容は下記をご覧ください。設定内容をコメントしています。
terraform-docs について
terraform-docs は Terraform のコードからドキュメントを自動生成するツールです。モジュールの requirements、providers、inputs、outputs、resources などの情報を README に自動出力するために使用しています。
README への出力結果と、設定ファイル .terraform-docs.yml は下記をご覧ください。
参考:
3. PR 作成時(GitHub Actions)
PR 作成時に GitHub Actions を起動し、すべての検証(fmt / validate / test / tflint / checkov)を実行します。結果は PR に出力されます。
なお、terraform fmt は -check -recursive -diff オプションをつけて、フォーマット違反がある場合は結果が FAILED になるようにしています。
GitHub Actions のワークフロー定義は下記をご覧ください。
4. デプロイ時(CI/CD パイプライン)
CI/CD パイプラインに terraform plan を実行する Plan ステージと、承認(Approval)ステージを組み込むことで、実際にインフラへ適用される変更内容を最終確認できます。パイプラインの流れは以下のとおりです。
1. Source — コードの取得
2. Plan — terraform plan -out=tfplan -input=false を実行して計画(tfplan ファイル)を作成し、アーティファクトストアに保存
3. Approval — Plan の結果を確認し、承認
4. Apply — terraform apply -input=false tfplan で tfplan ファイルに保存された計画を適用
Plan ステージで変更内容を可視化することで、意図しないリソースの削除や設定変更を適用前に検知できます。静的解析やモックテストではカバーしきれない、実際のインフラ状態との差分を確認します。
まとめ
静的解析・自動テスト・CI/CD を整備することで、コードの品質を保ちながら開発を加速できます。AI エージェントによるコーディングが広がる今、こうした自動検証の仕組みの重要性は一層増していると思います。
本記事で紹介した構成が、Terraform プロジェクトの品質担保の参考になれば幸いです。
