先に要点
- Terraform は HashiCorp が開発する クラウドインフラを宣言的なコード(HCL)で管理する IaC(Infrastructure as Code)ツール。AWS / GCP / Azure / Cloudflare など多数のプロバイダ対応で、事実上の標準。
- AWS 本番運用で最初に組む最小構成: 「 S3(State 保存) + DynamoDB(Lock) 」 「 VPC + Subnet 」 「 ALB + ECS Fargate or EC2 」 「 RDS or Aurora 」 「 IAM Role + OIDC(GitHub Actions 連携) 」。「最初に正しく組めば、後から散らかった構成を直す手間が圧倒的に減る」。
- State 管理は 「 リモートバックエンド(S3 + DynamoDB)」 が必須。「ローカル state は事故のもと」 「 「S3 にバージョニング + 暗号化」 「 DynamoDB で同時実行 Lock」 が現代の標準。個人開発でも最初からリモートバックエンドにする。
- 環境分離は ディレクトリ分離(envs/dev / envs/stg / envs/prod) + モジュール共通化 が王道。「Workspace で分ける」 は単純なケース以外で破綻しやすい。各環境は独立した state file を持つ のが安全。
- CI/CD は GitHub Actions の OIDC 連携で AWS にロール引き受け が現代の正解。「 長期 IAM アクセスキーを GitHub Secrets に置く」 のは非推奨(漏洩リスク)。「OIDC 経由なら一時クレデンシャル + 短期間有効」 で安全。
「AWS でちゃんとした本番環境を組みたい」 と思った瞬間に、インフラをコードで管理しないと、後で誰も触れない地雷になる という問題に当たります。コンソールでポチポチ作った構成は 再現性ゼロ」 「 環境ごとに微妙に違う」 「 誰が何を変えたか分からない 状態になりがちです。
Terraform は、「インフラを宣言的なコードで管理 → terraform plan で変更内容を確認 → terraform apply で適用」 という流れで、再現可能・レビュー可能・ロールバック可能なインフラ を実現します。HashiCorp が開発する OSS で、AWS / GCP / Azure / Cloudflare / Datadog など多数のプロバイダに対応する IaC のデファクトスタンダードです。
この記事では、AWS で 最小構成を Terraform で組む実装パターンを、「State 管理 / モジュール設計 / 環境分離 / CI/CD」 まで含めて整理します。IAM の使い分け と AWS 前段選択ガイド も併読すると、「どんな構成を Terraform で組むか」 のイメージが具体的になります。
Terraform の基本 — 何が嬉しいか
「なぜインフラをコードにするか」 の本質を最初に整理します。
再現性
「 同じ構成を別環境にも作れる(dev / stg / prod)」 「 「 災害時にゼロから再構築できる」。「コンソール手動構築では、構成図を見ても完全には再現できない」 のが現実。
レビュー可能
` Pull Request で 「terraform plan」 の差分をレビュー」。「 本番に何が起きるか」 を事前確認できる。「コンソール作業は誰も止められない」 が、コードなら 4 つの目を通せる。
State の管理 — 最初に決める最重要事項
Terraform で 最も重要なのが State(状態ファイル)の管理。「state がローカルにある = 個人開発以外では破綻」 する。
State とは
` Terraform が管理する 「実際のリソースの現状」 を JSON で保存したファイル」。「terraform.tfstate」 として保存される。コードと現状を突き合わせて差分を計算する ための核。
ローカル state の問題
「 個人 PC に state があると、他人が触れない」 「 PC 紛失で state ロスト」 「 複数人で同時に apply 競合」。本番運用では絶対 NG。
「 S3 バケットに state を保存(バージョニング + 暗号化必須)」 「 DynamoDB で同時実行 Lock(複数人の同時 apply を防止)」 が標準。個人開発でも最初からこれにする のが事故予防。
最小構成の組み立て
AWS 本番運用で 最初に作る最小構成を Terraform でコード化する流れ。
「最初から正しいディレクトリ構造とモジュール分割で始める」 のが、「後から散らかった構成を直す手間」 を圧倒的に減らします。
ディレクトリ構造の例
実プロジェクトでよく使うディレクトリ構造を示します。
| ディレクトリ / ファイル | 役割 |
|---|---|
| envs/dev/main.tf | dev 環境のエントリポイント。modules を呼び出す |
| envs/dev/backend.tf | S3 + DynamoDB バックエンド設定(環境ごとに別 state) |
| envs/dev/variables.tf | 環境固有の変数(インスタンスサイズ、ドメインなど) |
| envs/stg/... | stg 環境(dev と同じ構造) |
| envs/prod/... | prod 環境(dev / stg と同じ構造) |
| modules/vpc/ | VPC + サブネット + ルーティング |
| modules/compute/ | ECS Fargate / EC2 / Lambda の抽象モジュール |
| modules/database/ | RDS / Aurora / DynamoDB |
| modules/iam/ | IAM ロール / ポリシー |
| modules/observability/ | CloudWatch / アラーム / ログ |
「envs/* で環境ごとの設定 + modules/* で共通ロジック」 の分離が、環境差分を最小化しつつコードを再利用 する基本パターン。
環境分離 — Workspace vs ディレクトリ分離
「 環境分離の方法」 で迷うのが Terraform 経験者の通過儀礼。
「本番運用ではディレクトリ分離一択」 と考えて良いです。Workspace は 「小規模 / 検証用 / 完全同一構成」 に限定。
GitHub Actions + OIDC で CI/CD
「Terraform apply を GitHub Actions から実行」 する現代的な構成。
OIDC の利点
「 GitHub Actions が AWS に OIDC で認証 → 一時 IAM クレデンシャル取得 → terraform apply 実行」。長期 IAM アクセスキーを GitHub Secrets に置かない ので、「漏洩リスクが激減」。
PR ワークフロー
` PR 時に 「terraform fmt」 「 terraform validate」 「 terraform plan」 を自動実行 → 結果を PR コメントに投稿」。レビュアーが 「何が変わるか」 を一目で確認できる 体験。
apply の安全策
` main へマージで 「terraform apply」 が自動実行」 の前に、手動承認ステップ を入れるのが標準。「Environments の Required reviewers 機能」 で 「本番変更は別の人の承認必須」 にできる。
Atlantis / Spacelift / env0
「 Terraform 専用の CI/CD ツール」 もある。「PR コメントで apply / plan をトリガー」 「 Drift Detection」 などの高機能を提供。「チーム規模が大きくなったら検討」 の選択肢。
モジュール設計のコツ
「再利用しやすいモジュール」 を作るためのポイント。
入力を最小限に
「 必須変数だけ受け取り、それ以外はデフォルト値」。「変数が多すぎるモジュール」 は 使うのが大変で再利用されない。`デフォルト値を 「本番向け推奨設定」 にする」 のが定石。
出力を明示
「 モジュールから出力する値」 を 「outputs.tf」 で明示。「 モジュール利用側が必要な情報(ARN / ID / エンドポイント)」 を一覧で把握できるように。
過剰な抽象化を避ける
「 1 回しか使わないものをモジュール化するな」 が原則。2〜3 回使うと分かったタイミングでモジュール抽出 が現実的。「最初から抽象化」 すると 「用途が予測と外れて使いにくいモジュール」 になりがち。
バージョン管理
「 内部モジュールも git tag でバージョン管理」。「source = "git::...?ref=v1.2.0"」 のように 明示的にバージョン指定。「勝手にモジュールが更新されて壊れる」 事故を防ぐ。
ハマりやすいポイント
実装で踏みやすい落とし穴を整理します。
State Lock のデッドロック
「 terraform apply 中に Ctrl+C で中断 → DynamoDB Lock が残る」 → 次の apply ができない。「 terraform force-unlock
削除されたリソースの State 不整合
「 AWS コンソールで手動削除したリソース」 が 「terraform state」 に残ったまま。「terraform plan」 で 「絶滅したリソースをまた作ろうとする」。terraform state rm で state からも削除する必要。
Drift(コードと現状の乖離)
「 コンソールで誰かが手動変更 → コードと現状がずれる」。「定期的に terraform plan で Drift 検出」 する習慣を持つ。AWS Config + Drift Detection 機能 を併用すると自動化できる。
Terraform に関するよくある質問
Q. Terraform vs CloudFormation / CDK、どっちを選ぶ?
A. マルチクラウド or AWS 以外も使う = Terraform、AWS 専業 + 開発者中心 = CDK。CloudFormation は AWS 純正だが学習コストが高い。「Pulumi」 のような TypeScript / Python で書く選択肢もあるが、Terraform がエコシステムの大きさで最も実用的。
Q. 初心者は何から始めるべき?
A. S3 バケット 1 つを作るところから。「backend は最初ローカル」 でも OK、慣れたら S3 + DynamoDB に切り替え。小さく始めて、徐々に範囲を広げる のが挫折を避けるコツ。
Q. State ファイルの中身を直接編集しても良い?
A. 原則 NG。「terraform state」 コマンド(mv / rm / import)で操作する。「手動で JSON を書き換える」 と Terraform が認識できなくなる。「誤ったリソース管理対象から外したい」 は state rm、「既存リソースを Terraform 管理下に入れたい」 は import。
Q. 既存の AWS リソースを Terraform 管理下に入れたい
A. 「 terraform import」 で 1 リソースずつ取り込む。「terraformer」 のような OSS ツールで 既存環境を自動で Terraform コード化 もできる。「生成されたコードを整理 → 段階的にモジュール化」 が現実的なフロー。
Q. terraform apply で本番を壊しそうで怖い
A. PR レビュー必須 + plan の差分確認 + 手動承認ステップを必ず入れる。「destroy 系操作は special なフラグで限定」 する仕組みも有効。本番アカウントに対しては Read Only ロール + 別ロールで apply のような IAM 設計で 「事故率を下げる」。
Q. モジュールはどこまで再利用すべき?
A. 「 公開モジュール(Terraform Registry)」 を使う前に、信頼性を確認。「AWS 公式モジュール」 「 terraform-aws-modules(コミュニティ)」 は実績豊富。「自社モジュール」 は 同じ要件が 2〜3 回出てから抽出 が現実的。
Q. State Lock を強制解除した後、データが壊れないですか?
A. ほとんどのケースでは大丈夫ですが、「apply 中に強制解除 → 並行で別 apply 実行」 すると state が壊れる可能性。` 解除前に必ず 「誰も apply していない」 を確認。「AWS コンソールで進行中の変更が無いか」 も併せて確認するのが安全。
まとめ
Terraform で AWS 最小構成を組むときの本質は、最初から正しい State 管理・モジュール設計・環境分離・CI/CD を組むこと。「後で散らかった構成を直す」 のは想像以上に大変なので、最初に時間をかけて土台を作る ことが長期的なコスト削減になります。
「S3 + DynamoDB のリモートバックエンド」 「 envs/* + modules/* のディレクトリ構造」 「 GitHub Actions + OIDC の CI/CD」 が現代の AWS Terraform 運用の標準。「IAM の使い分け + AWS 前段選択」 と合わせて理解しておけば、「AWS を本格運用できるチーム」 として動けるようになります。
参考リンク
- HashiCorp: Terraform 公式
- HashiCorp Docs: AWS Provider
- Terraform Registry: terraform-aws-modules
- AWS Docs: GitHub Actions OIDC
- HashiCorp Learn: Terraform Best Practices