Instance Scheduler on AWS でタグ指定した Amazon EC2 インスタンスを定時起動・停止してみた
はじめに
テクニカルサポートの 片方 です。
開発環境や検証環境では、Amazon EC2 インスタンスを常時稼働させる必要がない場合があります。利用しない時間帯にインスタンスを停止し、必要な時間帯だけ起動することで、Amazon EC2 のコンピューティング料金を削減できます。
ただし、インスタンスを停止しても、Amazon EBS ボリューム、Amazon EBS スナップショット、Elastic IP アドレスなどには料金が発生する場合があります。停止によって削減できるコストの範囲は、事前に確認してください。
今回ご紹介する Instance Scheduler on AWS は、タグとスケジュール定義に基づいて、Amazon EC2 インスタンス、Amazon RDS DB インスタンス、EC2 Auto Scaling グループの稼働を自動化できる AWS Solutions のソリューションです。
リソースタグを利用してスケジュール対象を識別できるため、すべての Amazon EC2 インスタンスではなく、特定のタグを付与したインスタンスだけを制御できます。
本記事では、ap-northeast-1 の単一 AWS アカウントに Instance Scheduler on AWS をデプロイし、専用タグを付与した Amazon EC2 インスタンスだけを対象として、起動・停止を自動化します。
なお、本記事では、Amazon RDS、EC2 Auto Scaling グループ、クロスアカウント構成、クロスリージョン構成は扱いません。
検証環境について
今回は、Instance Scheduler on AWS で特定のタグを付与した Amazon EC2 インスタンスだけをスケジュール対象として、起動・停止できることを確認します。
検証には、単一の AWS アカウントおよび東京リージョン(ap-northeast-1)を使用します。Amazon RDS、EC2 Auto Scaling グループ、AWS Organizations を使用したクロスアカウント構成、クロスリージョン構成は対象外とします。
| 項目 | 内容 |
|---|---|
| AWS アカウント | 単一アカウント |
| AWS リージョン | ap-northeast-1 |
| スケジューリング対象 | Amazon EC2 インスタンス |
| 対象外 | Amazon RDS、EC2 Auto Scaling グループ、クロスアカウント、クロスリージョン |
| Instance Scheduler on AWS のデプロイ方式 | AWS CloudFormation の Hub Stack |
| スケジュール設定の保存先 | Amazon DynamoDB |
| スケジュールの評価間隔 | 5 分 |
| タイムゾーン | Asia/Tokyo |
| EC2 の EBS 暗号化 | AWS マネージド KMS キー |
| EBS 用の追加 KMS 設定 | 本検証では未設定 |
| 検証用タグキー | InstanceSchedulerTest |
| 検証用タグ値 | blog-test-schedule |
Instance Scheduler on AWS では、CloudFormation の Hub Stack をデプロイする際に、スケジュール判定に利用するタグキーを指定します。Amazon EC2 インスタンスに指定したタグキーを付与し、タグ値にスケジュール名を設定することで、対象インスタンスとスケジュールを関連付けます。
今回は、次のタグを付与した Amazon EC2 インスタンスだけを対象とします。
Key: InstanceSchedulerTest
Value: blog-test-schedule
InstanceSchedulerTest タグを持たない Amazon EC2 インスタンスは、本検証のスケジュール対象になりません。
また、スケジュール定義では Asia/Tokyo を明示し、スケジューラの実行間隔はデフォルトの 5 分とします。Instance Scheduler on AWS は指定した間隔で対象リソースの状態を評価するため、起動・停止は指定時刻ちょうどではなく、次回の評価タイミングで実行されます。
評価間隔を 5 分に設定した場合、通常は指定した開始・終了時刻から最大で約 5 分後に起動・停止します。そのため、検証時は開始時刻・終了時刻に余裕を持たせることをおすすめします。
なお、暗号化された Amazon EBS ボリュームをアタッチした Amazon EC2 インスタンスをスケジュールする場合、KMS キーの設定によっては、Instance Scheduler on AWS に KMS キーを使用するための権限が必要です。本検証では AWS マネージド KMS キーを使用し、追加の KMS 設定なしで起動・停止できることを確認しました。
カスタマー管理 KMS キーを使用する場合は、Hub Stack または Spoke Stack の KMS Key ARNs for EC2 に対象の KMS キー ARN を指定してください。これにより、スケジューリングロールに kms:CreateGrant などの必要な権限が付与されます。
構成図
AWS アカウント
└─ ap-northeast-1
├─ Instance Scheduler on AWS
│ ├─ AWS CloudFormation(Hub Stack)
│ ├─ Amazon EventBridge
│ ├─ AWS Lambda
│ └─ Amazon DynamoDB(スケジュール設定)
│
└─ Amazon EC2
├─ InstanceSchedulerTest=blog-test-schedule ← スケジュール対象
└─ タグなし、または異なるタグ値 ← スケジュール対象外
実装してみた
今回は、以下の流れで実装します。
- 検証用の Amazon EC2 インスタンスを作成する
- Instance Scheduler on AWS の Hub Stack をデプロイする
- AWS CloudFormation でスケジュールを作成する
- Amazon EC2 インスタンスにスケジュール用タグを付与する
- スケジューリングを有効化する
検証用の Amazon EC2 インスタンスを作成する
まず、スケジュールの対象となる Amazon EC2 インスタンスを 1 台作成しました。
今回の目的は起動・停止の確認のみのため、以下の構成としています。
| 項目 | 値 |
|---|---|
| AWS リージョン | ap-northeast-1 |
| AMI | Amazon Linux 2023 |
| インスタンスタイプ | t3.micro |
| ルートボリューム | Amazon EBS |
| EBS 暗号化キー | AWS マネージドキー |
| パブリック IPv4 アドレス | 無効 |
| セキュリティグループのインバウンドルール | なし |
| 初期状態 | stopped |
EC2 の起動・停止のみを検証するため、SSH や Session Manager によるログイン設定、インターネットからの到達性は不要としました。

Instance Scheduler on AWS の Hub Stack をデプロイする
続いて、Instance Scheduler on AWS を AWS CloudFormation でデプロイします。
Instance Scheduler on AWS は、Amazon EventBridge による定期実行、AWS Lambda によるスケジューリング処理、Amazon DynamoDB による設定情報の管理などで構成されます。Hub Stack をデプロイすると、これらのリソースが作成されます。
AWS マネジメントコンソールでリージョンを ap-northeast-1 に変更し、公式ドキュメントの Launch Solution から CloudFormation テンプレートを起動しました。テンプレートは以下よりダウンロードできます。
主なパラメータは以下のとおりです。
| パラメータ | 設定値 | 補足 |
|---|---|---|
| Stack name | instance-scheduler-test | 検証用のスタック名 |
| Namespace | blogtest | 複数デプロイを識別するための値 |
| Use AWS Organizations | No | 単一 AWS アカウントのため |
| Schedule tag key | InstanceSchedulerTest | スケジュール対象を判定するタグキー |
| Retain data and logs | Disabled | 検証終了時にリソースを削除しやすくするため |
| Enable scheduling | No | 初期設定中の意図しない起動・停止を防ぐため |
| Default time zone | Asia/Tokyo | 日本時間でスケジュールを定義するため |
| Scheduling interval (minutes) | 5 | デフォルト値 |
| Enable EC2 SSM maintenance windows | No | 今回は使用しないため |
| Create RDS instance snapshots on stop | No | Amazon RDS は対象外のため |
| Region(s) | ap-northeast-1 | スケジューリング対象のリージョン |
| KMS Key ARNs for EC2 | 空欄 | 本検証では追加設定なしで動作したため |
| Enable CloudWatch Debug Logs | Yes | 検証中にログを確認しやすくするため |
| Operational Monitoring | Disabled | 検証では追加コストを抑えるため |
| Log retention period (days) | 7 | 検証用のため短めに設定 |
Schedule tag key には、対象リソースを識別するタグキーを指定します。このタグキーは大文字・小文字を区別します。また、リソースに付与するタグの値には、後ほど作成するスケジュール名を設定します。
今回は、既存のタグ運用との競合を避けるため、汎用的な Schedule ではなく、以下の検証専用タグキーを指定しました。
InstanceSchedulerTest
また、設定中に EC2 インスタンスが操作されないよう、Enable scheduling は No としました。No を指定すると、すべてのスケジューリング操作が停止します。
スタックの作成後、ステータスが CREATE_COMPLETE になったことを確認しました。

CloudFormation でスケジュールを作成する
Instance Scheduler on AWS では、以下の要素を組み合わせて稼働時間を定義します。
- Period:インスタンスを起動状態にする日時・曜日・時刻
- Schedule:1 つ以上の Period とタイムゾーンをまとめた定義
- EC2 のタグ:適用する Schedule を指定する設定
今回は、22:15 から 22:30 までの 15 分間だけ EC2 インスタンスを起動するスケジュールを作成します。
スケジューラの実行間隔は 5 分に設定しているため、開始時刻・終了時刻ちょうどに状態が変わるとは限りません。検証時は、開始・終了時刻に余裕を持たせることをおすすめします。
CloudFormation コンソールから、スケジュール作成用のスタックを新規作成します。テンプレートには以下を使用しました。
AWSTemplateFormatVersion: '2010-09-09'
Parameters:
ServiceInstanceScheduleServiceTokenARN:
Type: String
Description: Instance Scheduler on AWS の Hub Stack の Outputs から取得した ServiceInstanceScheduleServiceToken の ARN
Resources:
BlogTestSchedule:
Type: Custom::ServiceInstanceSchedule
Properties:
ServiceToken: !Ref ServiceInstanceScheduleServiceTokenARN
# タグ値として利用するスケジュール名
Name: blog-test-schedule
# Hub Stack 名をスケジュール名の先頭に付与しない
NoStackPrefix: 'True'
Description: Schedule for Instance Scheduler on AWS blog verification
Timezone: Asia/Tokyo
# スケジュール外の状態を強制する
Enforced: 'True'
RetainRunning: 'False'
StopNewInstances: 'True'
Periods:
- Description: Run the test instance during the verification window
BeginTime: '22:15'
EndTime: '22:30'
WeekDays: mon-sun
ServiceInstanceScheduleServiceTokenARN には、先ほど作成した Hub Stack の [出力] タブに表示される ServiceInstanceScheduleServiceToken の値を指定します。
スケジュールを IaC で作成する場合、この ARN をカスタムリソースの ServiceToken に設定します。このテンプレートでは、以下のスケジュールを作成します。
| 項目 | 値 |
|---|---|
| Schedule 名 | blog-test-schedule |
| タイムゾーン | Asia/Tokyo |
| 起動開始時刻 | 22:15 |
| 停止開始時刻 | 22:30 |
| 対象曜日 | 月曜日~日曜日(mon-sun) |
| Enforced | True |
| RetainRunning | False |
| StopNewInstances | True |


Amazon EC2 インスタンスにスケジュール用タグを付与する
作成した blog-test-schedule を Amazon EC2 インスタンスへ適用します。
対象の EC2 インスタンスに、以下のタグを付与しました。
Key: InstanceSchedulerTest
Value: blog-test-schedule
タグキーの InstanceSchedulerTest は、Hub Stack の Schedule tag key で指定した値です。タグ値の blog-test-schedule は、CloudFormation で作成したスケジュール名です。
Instance Scheduler on AWS は、Hub Stack で指定したタグキーと一致するタグを持つリソースを認識し、タグ値に対応するスケジュールを適用します。
タグ値に存在しないスケジュール名を設定した場合は、UnknownSchedule エラーとなり、期待どおりに制御されません。その場合は、対象リソースの IS-Error タグと CloudWatch Logs を確認してください。
この時点では Hub Stack の Enable scheduling が No であるため、タグを付与しても EC2 インスタンスはまだ起動・停止されません。

スケジューリングを有効化する
最後に、Hub Stack の Enable scheduling を Yes に更新して、スケジューリングを有効化します。
CloudFormation コンソールで instance-scheduler-test スタックを選択し、[更新] から現在のテンプレートを使用して更新しました。このとき、次のパラメータだけを変更します。
| パラメータ | 更新前 | 更新後 |
|---|---|---|
| Enable scheduling | No | Yes |
スタックのステータスが UPDATE_COMPLETE となったことを確認して、設定は完了です。



なお、情報タグ付けが有効な場合、Instance Scheduler on AWS は管理対象として認識したリソースに IS-ManagedBy などの情報タグを追加します。このタグは、タグキー・タグ値・スケジュール名の対応が正しいことを確認する目安になります。
次のセクションでは、指定したスケジュールに従って EC2 インスタンスが起動・停止すること、および IS-ManagedBy などの情報タグや CloudWatch Logs を確認します。
確認してみた
今回は、以下のスケジュールを対象 EC2 に設定しました。
| 項目 | 設定値 |
|---|---|
| スケジュール名 | blog-test-schedule |
| タイムゾーン | Asia/Tokyo |
| 稼働時間 | 22:15 ~ 22:30 |
| 適用曜日 | Mon-Sun |
| Enforced | True |
| RetainRunning | False |
| StopNewInstances | True |
対象の Amazon EC2 インスタンスには、以下のタグを付与しています。
Key: InstanceSchedulerTest
Value: blog-test-schedule
InstanceSchedulerTest は Hub Stack の Schedule tag key に指定したタグキーです。また、blog-test-schedule はスケジュール用 CloudFormation スタックで作成した Schedule 名です。
スケジューリングを有効化すると EC2 インスタンスが停止した
対象の Amazon EC2 インスタンスを起動した状態で、Hub Stack の Enable scheduling を No から Yes に変更しました。
このときは、設定した稼働時間である 22:15 ~ 22:30 の時間外でした。そのため、Instance Scheduler on AWS がスケジュールを評価した結果、対象の EC2 インスタンスは停止しました。
今回の Schedule では、Enforced を True に設定しています。Enforced を有効にすると、稼働時間外に手動で起動されたインスタンスは、スケジューラによって停止されます。
また、稼働時間内に手動で停止したインスタンスは、次回のスケジュール評価時に起動されます。手動操作後もスケジュールに従った状態へ戻るため、本番環境で利用する場合は、運用ルールを事前に整理しておく必要があります。
StopNewInstances は True としています。この設定では、稼働時間外に起動中のインスタンスへ初めてスケジュール用タグを付与した場合、Instance Scheduler on AWS は当該インスタンスを停止します。
今回の結果から、Instance Scheduler on AWS は単に開始・停止時刻に処理を実行するだけではなく、スケジュールの評価時点で対象 EC2 インスタンスが稼働すべき状態かを判定し、必要に応じて状態を変更することが確認できました。
対象 EC2 インスタンスが管理対象として認識されたことを確認する
Instance Scheduler on AWS は、情報タグ付けが有効な場合、管理対象のリソースに IS-ManagedBy などの情報タグを付与します。
対象の EC2 インスタンスのタグを確認したところ、IS-ManagedBy タグが付与されていました。
IS-ManagedBy は、そのリソースを管理する Instance Scheduler on AWS の Hub Stack を示すタグです。対象リソースがスケジューリング用に登録された際に付与されます。
また、EC2 インスタンスを停止するアクションが実行された場合は、IS-LastAction に停止操作と UTC のタイムスタンプが記録されます。
IS-LastAction は、スケジューラが実際に開始または停止を行ったときに更新される情報タグです。

CloudWatch Logs を確認する
Hub Stack のデプロイ時に Enable CloudWatch debug logs を Yes に設定したため、Instance Scheduler on AWS の処理ログが Amazon CloudWatch Logs に出力されます。
スケジューリング処理のログは、以下の形式のロググループに出力されます。
<Hub Stack 名>-<Namespace>-scheduling-logs
そのため、今回の設定では、次のようなロググループ名になります。
instance-scheduler-test-blogtest-scheduling-logs
なお、スケジュール作成などの管理操作に関するログは、administrative-logs を含む別のロググループに出力されます。CloudFormation によるスケジュール作成時に問題が発生した場合は、こちらも確認してください。

稼働時間になると EC2 インスタンスが起動することを確認する
続いて、Schedule に設定した BeginTime を過ぎると、対象 EC2 インスタンスが running となることを確認します。
今回のスケジュールでは、22:15 ~ 22:30 が稼働時間です。そのため、スケジュールが有効な状態で 22:15 を過ぎると、停止中の対象 EC2 インスタンスは起動対象となります。
Instance Scheduler on AWS は、Hub Stack で設定した間隔でスケジュールを評価します。今回は評価間隔を 5 分に設定しているため、EC2 インスタンスの状態遷移は 22:15 ちょうどではなく、次回の評価タイミングで行われます。

IS-LastAction も、次のように更新されていました。
IS-LastAction
Started 2026-08-29 13:15:22 UTC
2026-08-29 13:15:22 UTC は、日本時間では 2026-08-29 22:15:22 JST です。設定した開始時刻以降に、対象 EC2 インスタンスが起動されたことを確認できました。
終了時刻後に EC2 インスタンスが停止することを確認する
EndTime を過ぎると、対象 EC2 インスタンスは停止対象となります。
今回は RetainRunning を False に設定しているため、スケジュールの終了時刻後は EC2 インスタンスが停止します。
RetainRunning は、スケジュール開始前から手動で起動していたインスタンスを、実行期間の終了後も稼働させ続けるかを制御する設定です。True に設定した場合、稼働時間前から手動で起動していたインスタンスは、稼働時間の終了後も停止されません。

IS-LastAction も、次のように更新されていました。
IS-LastAction
Stopped 2026-08-29 13:30:22 UTC
2026-08-29 13:30:22 UTC は、日本時間では 2026-08-29 22:30:22 JST です。設定した終了時刻以降に、対象 EC2 インスタンスが停止されたことを確認できました。
以上により、設定したスケジュールに従って、対象の Amazon EC2 インスタンスが起動・停止することを確認できました。
まとめ
Instance Scheduler on AWS を利用して、InstanceSchedulerTest=blog-test-schedule タグを付与した Amazon EC2 インスタンスだけをスケジュール対象にできることを確認しました。
また、スケジュール時間外にスケジューリングを有効化すると、起動中の対象 EC2 インスタンスが停止しました。
タグキーとスケジュール名を組み合わせることで、対象の Amazon EC2 インスタンスを限定して定時起動・停止できます。開発環境や検証環境のコスト最適化に有効です。
本番環境へ適用する場合は、以下の点を事前に確認してください。
- Enforced を有効にした場合、手動操作後もスケジュールに従ってインスタンスの状態が変更されること
- RetainRunning を有効にした場合、手動で起動したインスタンスが停止されず、継続稼働する可能性があること
- 停止後も Amazon EBS ボリュームや Elastic IP アドレスなどには料金が発生する場合があること
- 暗号化された Amazon EBS ボリュームを利用する場合、KMS キーに必要な権限を設定すること
- IS-ManagedBy、IS-LastAction、IS-Error などの情報タグを利用する場合、タグポリシーやタグ数上限に問題がないこと
- EC2 インスタンスのシャットダウン動作が stop に設定されていること
本ブログが誰かの参考になれば幸いです。
参考資料
- AWS インスタンスの開始と停止を自動化する - AWS での Instance Scheduler
- ステップ 1: Instance Scheduler ハブスタックを起動する - AWS での Instance Scheduler
- サンプルスケジュール - AWS での Instance Scheduler
- AWS CloudFormation テンプレート - AWS での Instance Scheduler
- オペレーターガイド - AWS での Instance Scheduler
クラスメソッドオペレーションズ株式会社について
クラスメソッドグループのオペレーション企業です。
運用・保守開発・サポート・情シス・バックオフィスの専門チームが、IT・AIをフル活用した「しくみ」を通じて、お客様の業務代行から課題解決や高付加価値サービスまでを提供するエキスパート集団です。
当社は様々な職種でメンバーを募集しています。
「オペレーション・エクセレンス」と「らしく働く、らしく生きる」を共に実現するカルチャー・しくみ・働き方にご興味がある方は、クラスメソッドオペレーションズ株式会社 コーポレートサイト をぜひご覧ください。※2026年1月 アノテーション㈱から社名変更しました








