★ 初級

11. データソース集

AWS Provider のうち、「読むだけ」 のデータソース。実物を作らずに既存リソースの情報を取得する仕組み。これらを覚えると、コードがハードコードから解放されて環境を移しやすくなります。

アカウント・リージョン情報

data "aws_caller_identity" "current" {}
data "aws_region" "current" {}
data "aws_partition" "current" {}

# よく使うパターン: ARN 組み立て
locals {
  account_id = data.aws_caller_identity.current.account_id
  region     = data.aws_region.current.name
  partition  = data.aws_partition.current.partition   # "aws" / "aws-cn" / "aws-us-gov"

  log_group_arn = "arn:${local.partition}:logs:${local.region}:${local.account_id}:log-group:/aws/lambda/hello"
}

aws_partition を使うと、中国リージョン(aws-cn)や GovCloud(aws-us-gov)を含むコードが書けます。普通は aws 固定で OK ですが、ARN を組む時は癖にしておくと安全。

アベイラビリティゾーン

data "aws_availability_zones" "available" {
  state = "available"

  # ローカルゾーンや Wavelength を除外
  filter {
    name   = "opt-in-status"
    values = ["opt-in-not-required"]
  }
}

# 使い方: 最初の 2 AZ にサブネットを作る
resource "aws_subnet" "public" {
  count             = 2
  vpc_id            = aws_vpc.main.id
  cidr_block        = "10.0.${count.index + 1}.0/24"
  availability_zone = data.aws_availability_zones.available.names[count.index]
}

AMI(最新・特定)

# Amazon Linux 2023 の最新
data "aws_ami" "al2023" {
  most_recent = true
  owners      = ["amazon"]

  filter {
    name   = "name"
    values = ["al2023-ami-*-x86_64"]
  }
}

# Ubuntu の最新
data "aws_ami" "ubuntu" {
  most_recent = true
  owners      = ["099720109477"]   # Canonical の AWS アカウント ID

  filter {
    name   = "name"
    values = ["ubuntu/images/hvm-ssd-gp3/ubuntu-noble-24.04-amd64-server-*"]
  }
}

# 自社で作った AMI(特定の名前パターン)
data "aws_ami" "internal" {
  most_recent = true
  owners      = ["self"]   # 自アカウント

  filter {
    name   = "name"
    values = ["myapp-*"]
  }
}

IAM ポリシー組み立て

data "aws_iam_policy_document" "lambda_assume" {
  statement {
    effect  = "Allow"
    actions = ["sts:AssumeRole"]
    principals {
      type        = "Service"
      identifiers = ["lambda.amazonaws.com"]
    }
  }
}

# 複数のポリシーを合成(merge)
data "aws_iam_policy_document" "merged" {
  source_policy_documents = [
    data.aws_iam_policy_document.s3_read.json,
    data.aws_iam_policy_document.dynamodb_rw.json,
  ]
}

ネットワーク既存参照

「会社共通の VPC があるので、それを使う」「既存の subnet を見つける」といった使い方。

data "aws_vpc" "main" {
  tags = { Name = "shared-main" }
}

data "aws_subnets" "private" {
  filter {
    name   = "vpc-id"
    values = [data.aws_vpc.main.id]
  }

  tags = { Tier = "private" }
}

# 使い方
resource "aws_instance" "worker" {
  subnet_id = data.aws_subnets.private.ids[0]
  # ...
}

Route 53 ホストゾーン

data "aws_route53_zone" "this" {
  name = "hcl-guide.com"
  # private_zone = false  # 必要に応じて
}

resource "aws_route53_record" "blog" {
  zone_id = data.aws_route53_zone.this.zone_id
  name    = "blog.hcl-guide.com"
  type    = "A"
  # ...
}

Secrets Manager / SSM Parameter Store

API キー・パスワードを .tfvars に書かず、Secrets Manager / SSM から取得します。

data "aws_secretsmanager_secret_version" "db" {
  secret_id = "myapp/db/master"
}

# 中身は JSON で入れる慣例
locals {
  db = jsondecode(data.aws_secretsmanager_secret_version.db.secret_string)
}

# locals.db.username, locals.db.password などとして使える
data "aws_ssm_parameter" "api_key" {
  name = "/myapp/external-api-key"
  # SecureString は自動で復号される
}

resource "aws_lambda_function" "x" {
  environment {
    variables = {
      API_KEY = data.aws_ssm_parameter.api_key.value
    }
  }
}
秘密が state に入る data ソースで取得した秘密は、Terraform の state ファイルに平文で保存 されます。state を S3 に置く時は 必ず暗号化(バケットの SSE-KMS)と アクセス制限(IAM、bucket policy)をかける。

KMS キー

data "aws_kms_alias" "ebs" {
  name = "alias/aws/ebs"
}

# 使い方: ボリュームをこの KMS キーで暗号化
resource "aws_ebs_volume" "data" {
  availability_zone = "ap-northeast-1a"
  size              = 100
  encrypted         = true
  kms_key_id        = data.aws_kms_alias.ebs.target_key_arn
}

ハードコード排除のコツ

Terraform 学習者がやりがちな「ハードコード」と、置き換える data:

ハードコード置き換え先
"123456789012"data.aws_caller_identity.current.account_id
"ap-northeast-1"data.aws_region.current.name
["ap-northeast-1a","1c"]data.aws_availability_zones.available.names
"ami-0c4..."data.aws_ami.al2023.id
"db_password = ..."data.aws_secretsmanager_secret_version
vpc_id = "vpc-xxx"data.aws_vpc.main.id

これだけで、コードは「環境を変えても動く」状態に近づきます。

AWS 編はここまで お疲れ様でした。HCL × AWS × GitHub の 3 領域で、Terraform の実務に必要な土台が揃いました。次は実際に ホーム から興味のあるトピックを行ったり来たりして、自分のプロジェクトで手を動かしてみてください。