[小ネタ]ImageBuilerで作成されたWindowsインスタンスイメージのタイムゾーンを常に「Tokyo Standard Time」にする方法
こんにちは!AWSエンジニアのおつまみです!
先日ImageBuilderを構築していた時に困った内容をシェアします!
困っていた内容
windows-server-2022-english-full-base-x86(最新版)
を使用したベースイメージで、タイムゾーンをUTC
→Tokyo Standard Time
に設定予定でした。
そのため、下記のカスタムコンポーネントでタイムゾーン設定を実施することにしました。
- name: SetTimeZone action: ExecutePowerShell onFailure: Continue inputs: commands: - | # 現在のタイムゾーンを取得 Write-Host 'Get current timezone...' Get-TimeZone | Select-Object Id, BaseUtcOffset | Out-String # タイムゾーンの変更 $timeZoneId = 'Tokyo Standard Time' # JSTに設定する場合(必要に応じて変更する) Write-Host 'Configure timezone...' Set-TimeZone -Id $timeZoneId | Out-String # 変更した結果を確認 Write-Host 'Get new timezone...' Get-TimeZone | Select-Object Id, BaseUtcOffset | Out-String
しかし、作成されたイメージからEC2インスタンスを起動すると、タイムゾーンがUTCに戻っている現象に陥りました。。
ログにも以下が出力されており、ビルド時点では問題なさそうでした。
2023-04-03T08:00:25.592147400Z Stdout: Id BaseUtcOffset 2023-04-03T08:00:25.592147400Z Stdout: -- ------------- 2023-04-03T08:00:25.592147400Z Stdout: UTC 00:00:00 2023-04-03T08:00:25.592147400Z Stdout: 2023-04-03T08:00:25.592147400Z Stdout: 2023-04-03T08:00:25.597644300Z Stdout: 2023-04-03T08:00:25.598287100Z Stdout: Configure timezone... 2023-04-03T08:00:25.599471200Z Stdout: 2023-04-03T08:00:25.604510700Z Stdout: Get new timezone... 2023-04-03T08:00:25.605692900Z Stdout: 2023-04-03T08:00:25.605692900Z Stdout: Id BaseUtcOffset 2023-04-03T08:00:25.605692900Z Stdout: -- ------------- 2023-04-03T08:00:25.605692900Z Stdout: Tokyo Standard Time 09:00:00
結論:なぜ戻ってしまったか?
- カスタムコンポーネントで定義した設定はbuildフェーズで実施される。
- build, testフェーズが終わると sysprep が実行される。
- sysprepが実行されると、sysprep 構成ファイル
Unattend.xml
で定義されているデフォルトのUTC
に戻されてしまう。 - そのため、カスタムコンポーネントではsysprep 構成ファイル
Unattend.xml
の変更が必要。
Sysprepとは?
Sysprep とは、Microsoft 社が提供する Windows OS を展開するためのシステム準備ツールです。
Windows インスタンスを複製する際に、そのまま AMI を取得すると、マシンSIDというユニークに付与されるIDが重複し、ライセンス認証に関する問題が発生する可能性があるなど、問題のひとつの要因になりえます。
そのためWindows ServerのAMIを作成する時は、Sysprepを実行することによって、Windowsのインストールイメージを準備し、他のコンピューターに展開することができます。
そして、このSysprepがImageBuilderでイメージを作成する時のフローに含まれています。
ImageBuilderのフローについて
ImageBuilderでWindowsインスタンスのイメージを作成した場合、このようなフローとなります。
順番 | ステップ名 | 実施内容 |
---|---|---|
1 | LaunchBuildInstance | Image Builderでカスタムイメージを作成するために使用されるインスタンスを起動します。 |
2 | ApplyBuildComponents | インストールする必要のあるソフトウェアコンポーネントをインストールします。 |
3 | InventoryCollection | パッケージやファイル、構成などの情報を収集します。 |
4 | RunSanitizeScript | 収集された情報を処理し、AMIを構成するための準備を行います。 |
5 | RunSysPrepScript | システムを準備し、オペレーティングシステムの汎用化を実行します。 |
6 | CreateOutputAMI | 新しいAMIを作成し、そのAMIのIDを出力します。 |
7 | TerminateBuildInstance | インスタンスを終了します。 |
結論でお伝えしたとおり、No.2のbuild, testフェーズ終了後に No.5のsysprep が実行されています。そのため、sysprepが実行されると、sysprep 構成ファイルUnattend.xml
で定義されているデフォルトのUTC
に戻されてしまうということでした。
対処方法
カスタムコンポーネント内でsysprep 構成ファイルUnattend.xml
の設定をUTC
→Tokyo Standard Time
に変更するよう設定します。
- name: build steps: - name: SetTimeZone-Region-DisplayLanguage action: ExecutePowerShell onFailure: Continue inputs: commands: - | # 構成ファイルの設定 Write-Host 'Configure timezone...' (Get-Content "C:\ProgramData\Amazon\EC2Launch\sysprep\Unattend.xml").replace('<TimeZone>UTC</TimeZone>', '<TimeZone>Tokyo Standard Time</TimeZone>') | Set-Content "C:\ProgramData\Amazon\EC2Launch\sysprep\Unattend.xml"
参考:AWS Image Builder - Setting the Timezone in a Windows Image | Tom’s blog
このコンポーネントを設定するようにImageBuilderを実行します。
作成されたイメージからEC2インスタンスを起動してみます。無事タイムゾーンがTokyo Standard Time
になっていました!
さいごに
今回はImageBuilerで作成されたWindowsインスタンスイメージのタイムゾーンを常に「Tokyo Standard Time」にする対処方法についてお伝えしました。
単純なタイムゾーンの設定だけでは、設定が元に戻ってしまうことにご注意ください。 Sysprepで設定している項目はタイムゾーン以外にもあるので、詳しくはこちらのブログをご参照ください。
最後までお読みいただきありがとうございました!
どなたかのお役に立てれば幸いです。
以上、おつまみ(@AWS11077)でした!