【NIC x Ops(にこぷす)通信】(Terraform編)【連載】本当に買い?HCP Terraform Premiumをゆるっと検証 〜気になる「運用自動化」と「ガバナンス」ってぶっちゃけどうなの?(全6回)
投稿者:種田
【第4回】コンソールから勝手に弄った奴は誰だ。ドリフト検知で「野良変更」は許さないよ
目次
- はじめに:クラウド運用の宿命「野良変更」の恐怖
- HCP Terraformの「Health Checks(ドリフト検知)」とは?
- 【検証】Google Cloud(Compute Engine)で「野良変更」を再現してみた!
- 自動修復までやる?「野良変更」への現実的な対応
- まとめ
- 次回予告
皆さま、こんにちは!
このテックブログでは、IT運用に関する内容を連載、「にこぷす通信」をお届けしています。
「NIC x Ops(にこぷす)」とは?
『NIC x Ops(にこぷす)』とは、
私たちの会社であるNTTインテグレーション(NI+C)の運用ノウハウと、
IBMさんの強力なソリューションを
Collaboration(コラボレーション)させた、IT運用高度化シリーズ(Ops)のニックネームなんです。
現代のIT運用の現場は、システムの複雑化や人手不足など、課題が山積みです。そんな現場を少しでも楽に、そしてエンジニアの皆さんが笑顔で「攻めの運用」ができるように支えたい。そんな想いがこの「にこぷす」には込められています。
「にこぷす」には、Instana(可観測性)のほかにも、Turbonomic(リソース最適化)やTerraform(インフラ自動化)など、IT運用を劇的に変える製品がたくさんあります。
これからもこの通信を通して、「IT用語は難しいけれど、中身を知ればこんなに便利で面白いんだ!」というテクニカルな内容をご紹介していきますので、どうぞよろしくお願いします。
1. はじめに:クラウド運用の宿命「野良変更」の恐怖
「Terraformでガッツリコード管理しているから、うちのインフラは100%安全!」
そう自信満々に言っていたはずなのに、ある日突然、誰かがGoogle Cloud(GCP)のコンソールからポチッと設定を変えていた……。インフラ管理者なら、そんな経験を一度はしたことがあるのではないでしょうか?
インフラをコード化(IaC)していても、障害対応の緊急メンテや「ちょっと確認するだけ…」という理由で、Webコンソールから直接手動で変更を加えてしまう、通称「野良変更」。
このコード( main.tf や State)と実環境(クラウド側)の設定がズレてしまう現象を、「ドリフト(Drift)」と呼びます。
このドリフトを放置しておくと、運用でこんな困ったトラブルを引き起こしてしまいます。
- セキュリティホールの発生:
コンソールで一時的に開けたポートやアクセス制限が放置され、誰も気づかないまま脆弱性に……。 - 次回
apply実行時の事故:
久しぶりにコードを修正してterraform applyを打ったら、誰かがコンソールで対応していた緊急回避用の設定が綺麗さっぱり上書き・削除され、サービス障害が再発! - 構成のブラックボックス化:
「コードを見ても現在の本当の状態が分からない」状態になり、IaC最大のメリットが崩壊。
クラウド運用において、この「野良変更(ドリフト)との戦い」は避けて通れない宿命なのです!
2. HCP Terraformの「Health Checks(ドリフト検知)」とは?
「じゃあ、管理者が毎日GCPコンソールとTerraformコードをにらめっこして監視しなきゃいけないの?」
当然、そんな人間わざの運用は不可能ですし、やりたくもありませんよね。
そこで登場するのが、HCP Terraform(有償プラン)の機能の一つ、「Health Checks(ドリフト検知)」です!
異変を嗅ぎつける「見守り役」
Health Checksの仕組みはシンプルかつ強力です。HCP Terraformが裏で定期的に terraform plan 相当の読み取り(Read-only)処理をバックグラウンドで自動実行し、「State(記録)とGCPの実環境にズレが生じていないか?」を定期的にチェックしてくれます。
もし誰かがコンソールから「野良変更」を加えると、HCP Terraformのダッシュボード上で対象のWorkspaceが Drift Detected(ドリフト検知!) と表示され、異変をいち早く管理者に教えてくれます。
💡 ワンポイント注意:即時(リアルタイム)検知ではない!
ここで押さえておきたいのが、Health Checksはコンソール操作の「数秒後」にリアルタイムで反応するわけではないという点です。
実行タイミングはHCP Terraform側が自動でコントロール(デフォルトで概ね1日1回ペース)しており、ユーザー側で「毎日何時に走らせる」といった細かいスケジュール指定はできません。
検証や緊急確認で今すぐ結果を見たいときは、画面上の 「Start health assessment」 ボタンを押して手動で評価を走らせましょう!
🛠️ 補足:実はAPI+スケジューラーで自作もできる…?
「定期的に plan を回して差分を見ているだけなら、HCP Terraformの Runs API(plan-only モード) を外部スケジューラーから定期的に叩けば自作できるのでは?」と思った方。鋭いです!個人レベルの小さなプロジェクトなら、実際これで代用できなくもありません。
ただし、対象(Workspace)やメンバーが増えてくると、以下の壁にぶち当たります。
- 実行キュー(Concurrency)の渋滞:
無償版(Freeプラン)だと同時実行数が基本的に1スロット(1枠)に限られています。そのため、自動スケジューラーのplanが走っている最中に開発者がgit pushや手動検証を叩くと、速攻でデプロイが詰まります。 - スケジューリング管理のカオス:
同時に実行できないため、スケジューラー側の設計が必要になります。Workspaceが増えるたびにスケジュールの設定を1つずつ追加・メンテナンスしなければならず、スケジューラーの管理自体がパンクして運用が回らなくなります。
通常のデプロイ用キューを塞ぐことなく、バックグラウンドの専用裏処理でサクッと並列評価し、ダッシュボードで一発可視化してくれる点こそが、有償機能(Health Checks)に頼る大きな価値なんです。
3. 【検証】Google Cloud(Compute Engine)で「野良変更」を再現してみた!
今回は実際の検証環境(Google Cloud)を使い、現場でありがちな「野良変更」を再現して、HCP Terraformがどう反応し、どうやって修復していくのかをテストしてみました!
🔹 事前準備:HCP TerraformでHealth Checksを有効化する
検証に入る前に、まずはHCP Terraform側でドリフト検知機能をオンにしておきます(組織レベルでドリフト検知を有効化することもできます)。
- 対象Workspaceの左メニューから Settings ➔ Health を開く
- Health Assessments の項目で 「Enable」 にチェックを入れる
- 「Save settings」 を押して保存!

これだけでドリフトをチェックしてくれるんです。
🔹 検証①:VMのマシンタイプを手動変更(単一リソースのドリフト検知)
ステップ1:コンソールから手動でマシンタイプを変更(野良変更)
まずは、コード(Terraform)で e2-micro として作成済みの Compute Engine(VM)に対し、GCPコンソールから手動で e2-small へマシンタイプを変更して保存してみます。
ステップ2:ドリフトチェックを手動実行
変更後、HCP Terraformの画面で 「Start health assessment」 ボタンを押し、手動でヘルスチェックを走らせてみます。

ヘルスチェックが完了すると、ダッシュボード上に検出された差分の内容が確認できるようになります!

ちなみに、今回はあらかじめメール通知を有効化しておいたため、ドリフトが検知された瞬間に以下のような通知メールが届きました。
内容は非常にシンプルなものですが、「Details」 ボタンを押せば、そのままHCP Terraformの差分詳細画面へ直接ジャンプできるため、画面を常時監視していなくても即座に異変へアクセスして調査に入ることができます。

また、「Explorer」画面で全Workspaceのドリフト状況を一発で一覧表示・俯瞰することも可能です。
🔍 差分の詳細を見てみると…?
話が脱線しましたが、検出された差分を確認してみると、手動変更したマシンタイプ(e2-micro ➔ e2-small)だけでなく、コード側で記述を省略していた instance_termination_action の値までも差分として検出されていました。

コードで明示していなかった属性(GCP側のシステムデフォルト値)が、ヘルスチェックの実行によって「コードに書いていないパラメータがstateに存在する」として露呈した格好です。意図したわけではなかったですが、ヘルスチェックによりコードの記述漏れパラメータを発見することができました。。
💡 コラム:いじってない設定まで検知された!?「隠れ差分」の正体
今回、手動変更したマシンタイプだけでなく、コードで記述を省略していた instance_termination_action まで差分として検出されて「えっ、そこ触ってないのに!?」と一瞬驚きました。
❓ そもそも、なぜ最初の terraform apply はエラーにならず通っていたの?
「コードに書いていないなら、作成時にエラーにしてよ!」と思いますよね。実はこの属性、GCP Provider側で Optional(任意項目) として定義されています。
記述を省略してデプロイしても、GCP側が裏でデフォルト値を補完して正常にVMを作ってしまうため、作成(apply)自体は一切エラーにならず何事もなく成功してしまいます。これがヘルスチェックの読み取り処理によって「隠れ差分」として露呈したわけです。
🛠️ どうやって解消する?
こうした補完値の差分は、実環境の最新状態をStateに反映する 「ステートのリフレッシュ(terraform apply -refresh-only)」を実行するだけでも解消(No drift化) できます!
ただ、今回の検証では「将来のデフォルト値変更による予期せぬ挙動を防ぎ、構成を明示的にコード管理する」という観点から、あえて コードにもしっかりと追記して追従させる形をとりました。
こうした「普段は気づきにくいデフォルト値の露呈」をサクッと洗い出し、Stateの同期やコードの見直しにつなげられるのも、定期的なヘルスチェックを回す大きなメリットですね!
ステップ3:コード側を修正して git push!
検知されたドリフトへの対応として、元々は「コンソールで手動変更されたマシンタイプ(e2-small)に合わせてコード側を修正(コード追従)しよう」と考えていました。
今回は偶然 instance_termination_action の記述漏れが判明したので、今回は、以下のように整理して対応することにします。
- 手動変更されたマシンタイプ(
e2-small):「野良変更はコードを正として元に戻す」方針としてコード側は書き換えず、元のe2-microへ強制リセットします。 - 未記述だった設定(
instance_termination_action):ヘルスチェックで発覚した記述漏れなので、この機会にmain.tfへしっかりと追記してコード管理下に置きます。
main.tf に instance_termination_action の設定を追記して Git リポジトリへ push すると、HCP Terraform 側で自動的に plan が実行されます。
実行結果のログを確認すると、狙い通り手動変更されていたマシンタイプが e2-small ➔ e2-micro へ引き戻され、追記した設定が反映される差分(1 to change)が出力されていることが確認できました!
内容に問題がないことを確認し、そのまま apply を実行して実環境を修正します。

ステップ4:ドリフト解消!見事 Healthy に復帰!
コードの修正と適用が完了したあと、再度ヘルスチェックの評価結果を確認してみると……

見事に No drift detected の表示に切り替わりました!
画面にも 「Your resource settings match those in Terraform configuration.(リソース設定はTerraform構成と一致しています)」 と明記され、コード・State・実環境の3者が正しく同期されたことがわかります。
手動変更されたマシンタイプは無事に本来の e2-micro へ復元され、未記述だった instance_termination_action もしっかりとコード管理下に置かれて平和が戻りましたね!
🔹 検証②:参照しているファイアウォールルールを手動変更したらどうなる?
VM単体の検証が終わったところで、VM側の Stateの中身を覗いてみたところ……「参照しているファイアウォールの情報も載っている」ことに気付きました。

今回の構成では、VM側のコードで data "terraform_remote_state" を使って共通ネットワーク側のワークスペースに定義したファイアウォールを参照しています。
ただ、State に載っているとはいえ、これはあくまで remote_state で他の Workspace を参照しているだけ。VM自体の設定が変わったわけではないので、参照先のファイアウォールをコンソールから変更しても、VM側のヘルスチェックには影響しない(ドリフトにならない)はずです。
実際どうなるのか、Cloud Console からファイアウォールルールを手動削除し、その後ファイアウォールルールのコードを修正して確かめてみます!
ステップ1:コンソールから手動削除
まずは Cloud Console から Terraform で作成済みのファイアウォールルールを直接手動削除し、VM側でヘルスチェックを実行してみました。
結果は予想通り、VM側ではドリフトは発生しませんでした!
ステップ2:FW側のコードを修正(追従)
続いて、参照先(FW側)のコードを追従・修正してルールを変更した状態でも、VM側でヘルスチェックを実行してみます。
こちらも予想通り、VM側ではドリフトは発生しませんでした!
参照先のリソース(FW)がどれだけ変更されても、VM自体の設定(構成)が変わっていない限り、VM側のWorkspaceとしては「正常(No drift)」と判断されるわけですね!
🔍 なぜ参照先が変わってもVM側では No drift なのか?
VM側のコードは remote_state を通して共通側を参照しているだけなので、VM自体の属性(マシンタイプやディスクなど)が直接変更されない限り、VM側の Workspace でドリフトは発生しません。
「参照先のリソースがコンソールで手動変更された(またはコードで更新された)」という異変は、そのリソースを直接管理している FW(共通)側の Workspace だけがピンポイントで捉えてくれる わけですね!
補足: ちなみに、コンソールから「新しいファイアウォールルールを新規追加」した場合は、Terraformの管理対象(State)に含まれていないため、ドリフトとしては検知されません。
コードにも
stateにも存在しないリソースは、Terraform から見れば「そもそも比較するstateが存在しない(視界に入っていない)」状態になるため、検知の対象外となります。
💡 コラム:Workspace分割(マルチWorkspace)と「爆発半径(Blast Radius)」の価値
もしインフラ全体(VPC、FW、VM、DBなど)が1つの巨大なstate(単一Workspace)に入っていたら、FWの野良変更1つのせいで全体が Drift Detected になり、修復の apply を打つのもどこに影響が出るか分からず恐怖になります。
Workspaceを「機能単位」で分割しておけば、「ドリフトが起きた範囲(FW側)だけをピンポイントで検知して、安全に修正できる」 という大きなメリットが生まれます!
📝 何がドリフト検知される?
ここまでの検証を踏まえて、「どんな変更ならドリフトとして検知され、何が対象外になるのか?」をパターン別に一覧表で整理してみました!
| 操作・対象 | 判定 | なぜそうなる?(理由・仕組み) |
|---|---|---|
|
管理対象リソースの手動変更・削除 (例: VMマシンタイプの手動変更) |
Drift |
State(管理台帳)の設定と実環境がズレるため 直接管理下にあるリソースの異変は確実にキャッチします。 |
|
コード記述漏れ(隠れ差分) (例: instance_termination_action の省略) |
Drift |
コードと State / 実環境で不整合が生じるため GCP側でデフォルト補完されていた設定がヘルスチェックで露呈します。 |
|
クラウド側のAPI更新による新パラメータ追加 (例: 新機能追加に伴うデフォルト値の発生) |
Drift |
コードに未記述の新しいデフォルト値がAPIから返るため 何も変更していなくても、API側のアップデートによって「身に覚えのない差分」として検知されることがあります。 |
|
参照先リソース(remote_state)の変更 (例: 参照先ファイアウォールの手動削除) |
No drift |
VM自体の設定は変わっていないため 参照先(FW側)の Workspace だけでピンポイント検知されます。 |
|
コンソールからの新規追加 (例: 新しいファイアウォールルールの追加) |
No drift |
State(管理台帳)に対象が存在しないため 比較する台帳自体がない(視界に入っていない)ため対象外となります。 |
4. 💡 自動修復までやる?「野良変更」への現実的な対応
「ドリフトを検知できるなら、そのまま自動で元通りに修復(Remediation)までやってほしい!」と一瞬思いがちですが、現実の運用を考えると「自動修復まで組み込むのはちょっと待った!」と言いたくなる理由がいくつもあります。
🙅♂️ 「自動復旧」を全面導入するのが難しい3つの理由
- 意図しない事故リスクがある(勝手に上書きされる怖さ)
例えば「障害対応で一時的に緊急回避用の設定を入れた直後」に自動修復が走ると、設定が消されて障害が再発してしまうリスクがあります。また、属性によってはapplyによってリソースが再作成(Re-create)されてしまう危険もあります。 - 「どれを自動で戻すか」の検討と運用が複雑になる
「このリソースは自動復旧でOK、こっちは影響が大きいからNG」といった対象の切り分け(ルール決め)が必要になり、システムが更新されるたびにそのルールのメンテナンスや検討コストが発生してしまいます。 - そもそもマネージド機能ではない(仕組みの面倒を見る必要がある)
HCP Terraformの Health Checks はあくまで「検知と通知」を行う機能です。自動修復をやるなら、Webhook を飛ばして外部の CI/CD(GitHub Actions等)やサーバーレス(Cloud Run/Lambda等)で自作スクリプトを動かす必要があり、今度は「その修復プログラムの保守・監視」という新たな運用負担が生まれてしまいます。
🛡️ 結論:現実的には「検知+通知」で人の判断を挟むのが一番安全&スマート!
このように、全自動化を目指して自作の仕組みを構築したり運用を複雑にするより、「異変をいち早く検知・通知してもらい、人間が状況を確認して判断する」 という運用に留めるのが、一番安全でコストパフォーマンスが良い選択になります!
「それでも、できる限り自動化を取り入れて日々の運用負担を下げたい!」という場合は、本番環境などへの適用は避け、万が一誤動作が起きても影響が出ない開発・検証環境や、一時的なリソースだけに「留めておく」のが無難です。
🤔 「元に戻す(引き戻し)」vs「コードを追従させる」の判断はどうする?
通知を受け取った人間が確認し、「変更された理由」に合わせて次のどちらかで対応します。
| 対応パターン | どんなとき? | 具体的なアクション |
|---|---|---|
|
元に戻す (引き戻し) |
・勝手に行われた野良変更 ・セキュリティ(FWやIAM)の無許可変更 |
コードが正(Source of Truth)。terraform apply を実行して、実環境を本来のコードの状態へ強制リセットします。
|
|
コードを追従 (コード修正) |
・障害対応での緊急コンソール操作 ・現地で試して正解だった設定変更 |
実環境の変更に正当な理由がある。 検知内容を元にコードを書き加えて PR を出し、コード側を最新化します。 |
5. まとめ
今回は、HCP Terraform の Health Checks(ドリフト検知)を使って「野良変更」をどう検知し、どう向き合っていくべきかを検証してきました。
最後に、今回のポイントを振り返っておきましょう!
- ドリフト検知は「全自動で直す魔法」ではなく「頼もしい見守り役」すべてを自動復旧させようとすると、自作スクリプトの保守やルールの検討コストがかさみ、運用の手間が増えてしまいます。「異変をいち早く察知して人間に教えてくれる存在」と割り切るのが一番スマートです。
- その State(管理台帳)に載っている変化だけをキャッチする手動変更はもちろん、コードの記述漏れやクラウド側のAPIアップデートによる新パラメータ追加もバッチリ検知してくれます。(※コンソールからの完全な新規追加や、別 Workspace の参照先変更は対象外となります)
- 「検知+通知 ➔ 人が判断して対処」が一番安全通知を受け取ったら、状況に合わせて「コード側を追従させる」か「
applyで強制リセットする」かを人間が判断して対応しましょう。
6. 次回予告
次回は「【第5回】消し忘れよ、さようなら。時間が来たら自動で消える「自動削除機能」が超便利だった」をお届けします!
「検証用に作った環境を消し忘れて放置し、月末のクラウド請求額を見て青ざめた……」なんて経験はありませんか?
次回は、あらかじめ指定した時間になるとリソースを自動で綺麗さっぱり削除(破棄)してくれる、HCP Terraformの「自動削除機能」を検証します!クラウドの無駄遣いと消し忘れ事故を防ぐ最強の味方の実力を、ガッツリお伝えします。次回もお楽しみに!
「にこぷす通信」について
「NIC × Ops(にこぷす)通信」は、隔週で皆さまに情報をお届けします。
このシリーズでは、Instana(可観測性)をはじめ、Turbonomic(リソース最適化)やTerraform(インフラ自動化)など、IT運用を劇的に変える製品をピックアップしていきます。
これからも最新の技術検証をチームで継続し、皆さまの現場ですぐに役立つ「有益な知見」を全力で共有していきます。 次回の連載もお楽しみに!