はじめに
手動でポートフォリオサイトを構築していましたが、「Infrastructure as Code」を学ぶためにTerraformを導入しました。AIとの対話で疑問を解決しながら、コードの暗記ではなく概念理解に重点を置いて学習した過程を記録します。
構築したもの
- ポートフォリオサイト: https://inatom-portfolio.com
- 技術構成: S3 + CloudFront + Route53 + ACM
- Infrastructure as Code: Terraform
- CI/CD: GitHub Actions
- 月額費用: 約500円
なぜTerraformを導入したのか
手動構築では設定の記録がなく、同じ構成を再現するのが困難でした。Terraformによって再現性、バージョン管理、チーム開発対応、CI/CDとの連携が可能になります。
学習アプローチ:AI活用による概念理解
Terraformの設定ファイルを丸暗記するのではなく、「なぜこの設定が必要なのか」をAIに質問しながら理解を深めました。実装中の疑問はリアルタイムで解決し、エラーメッセージの意味や最適な実装方法を学習しました。
実装手順と主なつまずきポイント
1. 環境構築での基本理解
tfstate管理用S3バケット作成
# AWSコンソールで専用バケット作成
# バージョニング有効化
疑問: 「なぜ専用のS3バケットが必要?」
AIとの対話で理解: tfstateファイルはTerraformの「記憶」で、ローカルPCだけでは他の環境から参照できない。S3で管理することでGitHub Actionsからも同じ状態を参照可能になる。
Terraformの基本設定
backend.tf
terraform {
backend "s3" {
bucket = "inatom-portfolio-terraform-state"
key = "portfolio/terraform.tfstate"
region = "ap-northeast-1"
}
}
provider.tf
provider "aws" {
region = "ap-northeast-1"
}
# CloudFront用SSL証明書はus-east-1必須
provider "aws" {
alias = "us_east_1"
region = "us-east-1"
}
つまずき: 「なぜus-east-1が必要?」
解決: CloudFrontで使用するACM証明書は必ずus-east-1に作成する必要があるAWSの制約。aliasを使用して複数プロバイダーを定義する方法を学習。
2. 既存リソースの取り込み:最大の難所
最初の大きな失敗
terraform plan
# Plan: 8 to add, 0 to change, 0 to destroy.
既存リソースが存在するのに、Terraformが「新規作成が必要」と判断。
根本的な理解: Terraformは自分が管理していないリソースの存在を知らない。手動で作成されたリソースは「存在しない」として扱われる。
terraform importの実践
# 既存リソースのID確認
aws cloudfront list-distributions
aws route53 list-hosted-zones
aws acm list-certificates --region us-east-1
# リソースをTerraform管理下に取り込み
terraform import aws_s3_bucket.portfolio inatom-portfolio.com
terraform import aws_cloudfront_distribution.portfolio E1P62XGQRY77C3
terraform import aws_route53_zone.portfolio Z02172211G84ZLOYNO3D6
3. Route53レコードの競合エラー
最大のつまずき:
Error: creating Route53 Record: [Tried to create resource record set but it already exists]
terraform apply実行中に突然エラー。一部リソースは作成済み、一部は失敗という中途半端な状態。
解決プロセス:
DNSレコードもTerraformリソースとして管理される。ホストゾーンをimportしても、個別のレコードは別途importが必要。
# 既存レコード確認
aws route53 list-resource-record-sets --hosted-zone-id Z02172211G84ZLOYNO3D6
# 競合するレコードをimport
terraform import aws_route53_record.portfolio_a Z02172211G84ZLOYNO3D6_inatom-portfolio.com_A
4. GitHub Actions CI/CD構築
セキュリティ設定
GitHub Secretsでアクセスキーを暗号化保存し、専用IAMユーザーを作成。学習段階ではAdministratorAccessを使用。
ワークフロー設定
name: 'Terraform'
on:
push:
branches: [ "main" ]
paths:
- 'terraform/**'
jobs:
terraform:
runs-on: ubuntu-latest
defaults:
run:
working-directory: ./terraform
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Configure AWS credentials
uses: aws-actions/configure-aws-credentials@v4
with:
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
aws-region: ap-northeast-1
- name: Terraform Apply
if: github.ref == 'refs/heads/main'
run: terraform apply -auto-approve
学習ポイント: paths指定により、HTMLファイル変更時にTerraformワークフローを実行しない効率化。
学んだ重要な概念
Infrastructure as Codeの価値
- .tfファイル = 「あるべき状態」の定義
- tfstateファイル = 「現在の状態」の記録
- terraform apply = 「あるべき状態」に合わせて「現在の状態」を変更
AI活用による効率的な学習
- コードの暗記ではなく、設定理由の理解を重視
- エラーメッセージをAIに質問して即座に理解
- 複数の解決方法をAIと検討して最適解を選択
運用での変化
Before(手動):
- インフラ変更: 30分-1時間の手作業
- 設定ミスのリスク
- 変更履歴なし
After(Terraform + GitHub Actions):
- コード変更 → git push → 自動反映
- 設定ミスの大幅削減
- 全変更をGit履歴で追跡可能
まとめ
手動構築からInfrastructure as Codeへの移行は、最初は複雑でしたが、terraform importを使った既存リソースの取り込みにより、サービス停止なしに移行できました。
AIとの対話により、Terraformの設定ファイル暗記ではなく、「なぜこの設定が必要か」の概念理解を重視した学習ができました。実際の開発現場でも、完璧な暗記より効率的な情報収集・問題解決が重要です。
今後はTerraformモジュール化やマルチ環境対応など、より実践的な運用に取り組む予定です。