terraform apply -targetの使い所と危険な乱用パターン|ピンポイント変更の判断基準と安全な運用設計

宮崎智広 この記事の監修:宮崎智広(Linux実務・教育歴20年以上・受講者3,100名超)
HOMELinux技術 リナックスマスター.JP(Linuxマスター.JP)Terraform > terraform apply -targetの使い所と危険な乱用パターン|ピンポイント変更の判断基準と安全な運用設計
「terraform apply -targetを使えば一部だけ先に適用できて便利だな」
そう思って使い始めたところ、次の全体適用でサービス断が発生した——現場でよく聞くインシデントです。

`terraform apply -target` は、Terraform のオプションのなかでも「正しく使えば有効、乱用すると危険」の差が最も大きい機能の一つです。公式ドキュメントでも「通常運用での使用は推奨しない(escape hatch)」と明記されているにもかかわらず、日常的に使ってしまっているチームが後を絶ちません。

この記事では、`-target` の仕組みと正当な使い道、危険な乱用パターン、そして `-target` に頼らなくて済む設計への移行方法を実務目線で解説します。Terraform 1.8系 / RHEL 9.4 環境で動作確認しています。

この記事のポイント

・terraform apply -targetは「緊急避難のオプション」であり通常運用向けではない
・乱用するとtfstateの整合性が崩れ、次の全体applyで予期しない変更が発生する
・正当な用途は「壊れたリソースのピンポイント再作成」「ドリフトした単一リソースの修正」の2つ
・-targetに頼る設計はモジュール分割やdepends_onで根本解決できる


「このままじゃマズい」と感じていませんか?
参考書を開く気力もない、同年代に取り残される不安——
でも安心してください。プロのエンジニアはコマンドを暗記していません。
「現場で使える型」を効率よく使いこなしているだけです。
姓・名・メールの3つだけ/30秒/解除は3秒 / 詳細はこちら

terraform apply -targetとは何か

`terraform apply -target` は、Terraform の変更適用を特定のリソース(またはモジュール)のみに絞り込むオプションです。

通常の `terraform apply` はステートファイル全体を参照してすべての差分を適用しますが、`-target` を使うと指定したリソースだけを操作対象にできます。

# 特定リソースのみ適用 terraform apply -target="aws_instance.web" # モジュール全体を対象にすることもできる terraform apply -target="module.vpc" # 複数指定も可能 terraform apply -target="aws_instance.web" -target="aws_security_group.app"

実際に `terraform plan -target` を実行すると、指定したリソースに関連する差分だけが表示されます。以下は本番環境で特定EC2インスタンスのインスタンスタイプ変更をピンポイントで確認した出力例です。

$ terraform plan -target="aws_instance.web" Terraform used the selected providers to generate the following execution plan. Resource actions are indicated with the following symbols: ~ update in-place Terraform will perform the following actions: # aws_instance.web will be updated in-place ~ resource "aws_instance" "web" { ~ instance_type = "t3.micro" -> "t3.small" id = "i-0a1b2c3d4e5f67890" tags = { "Name" = "web-prod-01" "Env" = "production" } # (28 unchanged attributes hidden) } Plan: 0 to add, 1 to change, 0 to destroy. ╷ │ Warning: Resource targeting is in effect │ │ You are creating a plan with the -target option, which means that the │ result of this plan may not represent all of the changes required to │ synchronize your real infrastructure with your configuration. │ │ The -target option is not for routine use, and is provided only for │ exceptional circumstances such as recovering from errors or mistakes. ╵

末尾の `Warning: Resource targeting is in effect` が重要です。Terraform 自体が「ターゲット指定モードで動作中」と警告を出しています。この警告を無視して日常的に使い続けるのが事故の温床になります。

-targetが正当に使える場面

1. 壊れたリソースのピンポイント再作成

本番環境で特定のリソースだけが壊れており、他のリソースへの影響を最小化して再作成したい場面で有効です。`terraform taint` でリソースを再作成対象にマークしてから `-target` で適用するパターンです。

# Terraform 1.x 以降: taint は非推奨。-replace を使う $ terraform apply -replace="aws_security_group.app" -target="aws_security_group.app" # Terraform 0.15.x 以前の場合 $ terraform taint aws_security_group.app $ terraform apply -target="aws_security_group.app"

障害対応・緊急修正の文脈で許容される使い方です。ただし使用後は必ず全体 plan で整合性を確認してください(後述)。

2. ドリフトした単一リソースの修正

手動操作(コンソール直接変更等)でドリフトが発生した特定リソースだけをコード定義に戻したい場合です。

# まずドリフトの内容を確認 $ terraform plan -refresh-only -target="aws_security_group.app" # 確認後、対象リソースのみコード定義に戻す $ terraform apply -target="aws_security_group.app" Apply complete! Resources: 0 added, 1 changed, 0 destroyed.

全リソースのドリフト確認(`terraform plan -refresh-only`)を実行する余裕がない緊急時に有効です。

3. 大規模なモジュール追加の一時的な段階確認

新しいモジュールを追加して全体 plan を実行したとき、差分が多すぎて確認しきれない場合にモジュール単位で分割して確認・適用するケースがあります。

ただしこれは「一時的な対処」であり、本来はモジュールを別ルートに分離することが正しい設計です。

-targetの危険な乱用パターン

1. ステートの整合性が崩れる

`-target` を使って一部のリソースだけを適用すると、ステートファイルが「中途半端な状態」になります。他のリソースとの依存関係が更新されないまま、特定のリソースだけが変更されるためです。

実際のインシデント例として、ECSタスク定義のみを `-target` で更新し、ALBのターゲットグループは旧設定のまま放置したケースがあります。次の `terraform apply`(全体適用)でALBが予期しない再設定を受け、本番サービスが2時間停止しました。

# 危険なパターン: ECSタスク定義のみ適用 $ terraform apply -target="aws_ecs_task_definition.app" # ALBのターゲットグループとの依存関係は更新されていない状態で... # 後日、全体applyを実行すると $ terraform apply # → ALBの設定が予期しない内容で変更されサービス断

2. 「一時的な使用」が常態化する

「今回だけ」で使った `-target` がチームの慣習になってしまうケースが非常に多いです。

コードには `aws_rds_cluster` と `aws_elasticache_cluster` の両方が定義されているが、RDSだけ先に作って ElastiCache は後でと言いながら、両者の依存部分が中途半端なまま何週間も経過する——こうした状況が現場でよく起きます。

3. planとapplyの乖離が発生する

CIパイプラインで `terraform plan` の結果を確認してから `terraform apply` を承認する運用をしている場合、`-target` を使ったapplyは「承認した内容と異なる変更が入る」状態を作り出す可能性があります。

# NG: planは全体、applyはターゲット指定(別物になる) $ terraform plan # 全リソースの差分を確認してチームがレビュー承認 $ terraform apply -target="aws_instance.web" # 一部のみ適用 # → レビューした内容と適用内容が一致しない状態になる

4. 公式の警告を「無視」する習慣がつく

HashiCorp の公式ドキュメントには以下の記述があります。

The -target option is an escape hatch for exceptional situations, and by using it in this way you are doing something that Terraform normally would not allow, and potentially bypassing important safety checks.」(-target は例外的な状況のための逃げ道であり、Terraform が通常許可しないことを実行しており、重要なセーフティチェックをバイパスする可能性がある)

この警告を毎回読み飛ばしているうちに、セーフティチェックの重要性への感覚が麻痺していきます。
現場で通用する安全なLinuxサーバー構築の「型」を体系的に身につけたい方へ、Terraform の設計パターンから apply 運用の安全設計まで、ハンズオン形式で体系的に学べるセミナーを開催しています。
>> Terraform実践セミナーの詳細はこちら

-targetに頼らない設計パターン

1. モジュール分割で「部分適用の必要性」をなくす

「一部だけ先に適用したい」という要求の多くは、モジュールの粒度が粗いことが原因です。VPC・コンピュート・データ層を別モジュールに分割すると、モジュール単位で安全に適用できます。

# modules/ を責務で分割する例 module "network" { source = "./modules/network" } module "compute" { source = "./modules/compute" vpc_id = module.network.vpc_id subnet_ids = module.network.private_subnet_ids } module "data" { source = "./modules/data" subnet_ids = module.network.private_subnet_ids }

モジュール単位の `-target`(`-target="module.network"`)はランダムなリソース指定より安全です。さらに進めて、ルートモジュールを完全に別ディレクトリに分離する(environments/dev/network/ 等)と、-target なしで環境ごとに安全な適用ができるようになります。

2. depends_onで依存関係を明示する

リソース間の依存が暗黙になっているため `-target` に頼ってしまう場合、`depends_on` で明示することで Terraform が正しい順番で自動適用するようになります。

resource "aws_security_group" "app" { name = "app-sg" vpc_id = aws_vpc.main.id # ... } resource "aws_instance" "web" { ami = "ami-0c55b159cbfafe1f0" instance_type = "t3.micro" # 暗黙依存では不十分な場合に明示する depends_on = [aws_security_group.app] }

3. terraform planの差分を読む力をつける

`-target` に逃げる最大の理由の一つは「全体 plan の差分が多くて怖い」という心理的な問題です。差分を正確に読む習慣をつけることで、不必要な `-target` 使用を避けられます。

Plan の `~`(update)と `+/-`(replace)を区別する:`~` はインプレース変更でサービス断なし、`+/-` はリソース再作成でサービス断あり
大きな差分は `terraform plan -out=plan.tfplan && terraform show -json plan.tfplan | jq` でJSON化して確認:差分の全量を把握してから適用判断する
CIのplan結果をPRにコメントで表示:atlantis や GitHub Actions でplanをコードレビューの一部にすることで「怖いから-target」を回避できる

-targetでステートが乱れた場合のトラブル対処と安全な使用フロー

「-targetは絶対禁止」ではなく「適切な文脈でのみ使う」が正しい姿勢です。緊急時に `-target` を使う場合の安全な手順を示します。

1. 使用前に全体planを保存する

# ターゲット指定の前に全体の差分を保存しておく $ terraform plan -out=full.plan $ terraform show full.plan > full_plan_before_target.txt # その後ターゲット指定でapply $ terraform apply -target="aws_instance.web"

2. 使用後に全体planでクリーンアップを確認する

# -target apply後、必ず全体planで差分残りがないか確認 $ terraform plan # 差分が残っている場合は速やかに全体適用する # (放置するとステート整合性が崩れたまま時間が経過する) $ terraform apply

3. 使用記録をチケット・コメントに残す

「なぜ -target を使ったか」「使用後の全体plan確認結果」をチケットやコメントに記録します。ドキュメントなしで `-target` が習慣化するのが最大のリスクです。

本記事のまとめ

項目 内容
-targetの本来の位置づけ 緊急避難の「escape hatch」。通常運用での使用は公式非推奨
正当な用途1 壊れたリソースの緊急再作成(-replace と組み合わせて使う)
正当な用途2 ドリフトした単一リソースのコード定義への修正
危険な乱用パターン 日常的な部分適用・planとapplyの乖離・ステート整合性の崩壊
根本解決の設計 モジュール分割・depends_on明示・CI/CDでのplan可視化
緊急時の最低限のルール 使用前に全体planを保存 → 使用後に全体planで整合性を確認
`terraform apply -target` を「便利な部分適用ツール」として日常的に使っているなら、それはコード設計やモジュール分割に改善余地があるサインです。根本的にはインフラのレイヤー分割と依存関係の明示化で解決できます。

Terraform の設計パターンをさらに深めたい方は、以下の関連記事も参照してください。

Terraformのmoduleとfor_each・countで構成を再利用する設計パターン
Terraformのlifecycleブロックで本番リソースを誤削除から守る方法
Terraformのplan・applyエラーを調査・解決する方法|TF_LOG・Stateロック・ドリフトを実践的に切り分ける
現場で通用する安全なLinuxサーバー構築の「型」を体系的に身につけたい方へ、Terraform の設計パターンと安全な apply 運用を実際に手を動かして学べるハンズオンセミナーを開催しています。
>> Terraform実践セミナーの詳細はこちら

無料メルマガで学習を続ける

Linuxの実践スキルをメールで毎週お届け。
登録は30秒、解除もいつでも可。

登録無料・いつでも解除できます

暗記不要・1時間後にはサーバーが動く

3,100名以上が実践した「型」を無料で公開中

プロのエンジニアはコマンドを暗記していません。
「現場で使える型」を効率よく使いこなしているだけです。
その「型」を図解60Pにまとめた入門マニュアルを、完全無料でプレゼントしています。

姓・名・メールの3つだけ/30秒/解除は3秒 / 詳細はこちら

Linux無料マニュアル(図解60P) 名前とメールで30秒登録
宮崎 智広

この記事を書いた人

宮崎 智広(みやざき ともひろ)

株式会社イーネットマーキュリー代表。現役のLinuxサーバー管理者として20年以上の実務経験を持ち、これまでに累計3,100名以上のエンジニアを指導してきたLinux教育のプロフェッショナル。「現場で本当に使える技術」を体系的に伝えることをモットーに、実践型のLinuxセミナーの開催や無料マニュアルの配布を通じてLinux人材の育成に取り組んでいる。

趣味は、キャンプにカメラ、トラウト釣り。好きな食べ物は、ラーメンにお酒。休肝日が作れない、酒量を減らせないのが悩み。最近、ドラマ「フライトエンジェル」を観て涙腺が崩壊しました。