AWS リソースを Terraform で管理しているチームで、複数人が同じインフラに対して terraform apply を実行する運用を始めます。tfstate ファイルの扱いとして最も適切なのはどれですか?
解説
Terraform の tfstate ファイルは、コードで宣言したリソースと AWS 上の実リソースを紐付ける「現在の状態の記録」です。次回 apply 時の差分計算に必須なので、無くしたり古い状態で上書きしたりすると、リソースの重複作成や意図しない削除といった事故につながります。チーム開発では S3 バックエンド(リモートステート)に保存し、さらに DynamoDB を使ったstate lockを有効にするのが定石です。lock があることで、誰かが apply 中に別の人が同時に apply して tfstate が壊れる事態を防げます。選択肢Aの Git コミットは、tfstate に DB パスワードや API キーなど機微情報が平文で含まれることがあるため危険です。さらに Git では同時 apply のロックができません。選択肢Cの手動同期は競合と人為ミスの温床です。選択肢Dの「tfstate 不要」は誤りで、これが無いと Terraform は何を管理しているか判断できません。backend ブロックの書き方terraform { backend "s3" { bucket = "my-tfstate-bucket" key = "prod/terraform.tfstate" region = "ap-northeast-1" dynamodb_table = "terraform-locks" encrypt = true } }ポイントは encrypt = true で S3 の保存時暗号化を有効にすること、そして dynamodb_table でロック用テーブルを指定することです。DynamoDB テーブルは LockID という文字列型のプライマリキーを1つ持つだけのシンプルなもので構いません。tfstate に何が書かれているのかtfstate は JSON 形式で、各リソースの ID・属性・依存関係などが記録されています。たとえば aws_instance を作成すると、EC2 インスタンス ID やプライベート IP、attach された EBS ボリュームの情報がそのまま入ります。RDS のマスターパスワードなど Sensitive な値も平文で記録されるため、tfstate へのアクセス権は IAM で厳格に制限する必要があります。S3 バケットには Block Public Access を設定し、バージョニングを有効にしておくと、誤って壊した場合のロールバックも可能になります。terraform plan が「差分なし」を出す仕組みTerraform は apply のたびに「コード(HCL)」「tfstate」「実際の AWS リソース」の3者を突き合わせて差分を計算します。tfstate が古いと「コードどおりなのに変更扱いになる」「すでに削除済みのリソースを再作成しようとする」といった現象が起きます。リモートステート + ロックを採用すれば、誰が apply しても常に最新の tfstate を参照できるため、こうした事故を構造的に防げるのです。