1. 概要
timecmp— 2つのタイムスタンプを比較するplantimestamp— planのタイムスタンプを返す(Terraform 1.5+)timestamp()との違いと使い分け
2. timecmp — タイムスタンプを比較する
timecmp(timestamp_a, timestamp_b)は2つのRFC 3339形式のタイムスタンプを比較します。a < bのとき-1、a == bのとき0、a > bのとき1を返します。
# terraform consoleで確認
> timecmp("2026-01-01T00:00:00Z", "2026-06-01T00:00:00Z")
-1 # a < b
> timecmp("2026-06-01T00:00:00Z", "2026-01-01T00:00:00Z")
1 # a > b
> timecmp("2026-06-01T00:00:00Z", "2026-06-01T00:00:00Z")
0 # a == b
有効期限が切れているかチェックする
terraform {
required_version = ">= 1.9"
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
}
}
provider "aws" {
region = "ap-northeast-1"
}
variable "environment" {
description = "環境名"
type = string
default = "dev"
}
variable "policy_expiry_time" {
description = "ポリシーの有効期限(RFC 3339形式)"
type = string
default = "2026-12-31T23:59:59Z"
}
locals {
# 有効期限が現在時刻より過去かどうかをチェック
# timecmp(policy_expiry, now) < 0 → 有効期限切れ
is_expired = timecmp(var.policy_expiry_time, timestamp()) < 0
}
resource "terraform_data" "expiry_check" {
lifecycle {
precondition {
condition = !local.is_expired
error_message = "ポリシーの有効期限(${var.policy_expiry_time})が切れています。"
}
}
}
data "aws_ami" "amazon_linux_2023" {
most_recent = true
owners = ["amazon"]
filter {
name = "name"
values = ["al2023-ami-*-x86_64"]
}
}
resource "aws_instance" "web" {
ami = data.aws_ami.amazon_linux_2023.id
instance_type = "t3.micro"
root_block_device {
volume_size = 20
volume_type = "gp3"
encrypted = true
}
tags = {
Name = "${var.environment}-web"
Environment = var.environment
ManagedBy = "terraform"
PolicyExpiry = var.policy_expiry_time
}
}
3. plantimestamp — planのタイムスタンプ(Terraform 1.5+)
plantimestamp()はTerraformがplanを実行した時刻を返します。timestamp()との違いは、plantimestamp()はplan中に固定されるためapply時に値が変わらない点です。
# terraform consoleで確認
> plantimestamp()
"2026-06-06T12:00:00Z" # planの実行時刻(apply中も同じ値)
locals {
# plantimestamp()はplan実行時刻で固定される(apply時に変わらない)
plan_time = plantimestamp()
# timestamp()はapplyのたびに変わる(driftの原因になる)
# apply_time = timestamp() # ← これは使わない
}
resource "aws_s3_bucket" "app" {
bucket = "${var.environment}-app"
tags = {
Name = "${var.environment}-app"
Environment = var.environment
ManagedBy = "terraform"
LastPlanTime = local.plan_time # planのタイムスタンプで固定
}
}
4. timestamp() vs plantimestamp() vs variable
| 方法 | plan時 | apply時 | 用途 |
|---|---|---|---|
timestamp() | 実行時刻 | apply時刻(異なる) | タグ程度の用途に限る |
plantimestamp() | plan時刻 | plan時刻(同じ) | planとapplyで一致が必要な場合 |
variableで渡す | 固定値 | 固定値 | 有効期限など固定が必要な値 |
5. 関連記事
- timestamp / formatdate / timeadd の使い方 — 日時関数の基本
- precondition / postcondition — timecmpでの有効期限チェック
- variable の validation ブロック — 日時のバリデーション
- locals(ローカル値)— DRYなコードを書く
- resourceブロック — 基本構文と使い方
- join / split / format / replace — 文字列操作
6. まとめ
timecmp(a, b)— タイムスタンプの比較。-1(a0(a==b)、1(a>b)を返すtimecmp(expiry, timestamp()) < 0で有効期限切れをチェックできるplantimestamp()(1.5+)はplan実行時刻で固定。timestamp()のdrift問題を回避できる- 固定の日時が必要な場合は
variableで外から渡すのが最も安全
動作確認バージョン: Terraform >= 1.9 公式ドキュメント: https://developer.hashicorp.com/terraform/language/functions/timecmp