しばたテックブログ

気分で書いている技術ブログです。

HTTPで時刻同期を行う方法について

注意事項 (2021年4月5日追記)

NICTによるHTTP/HTTPSを使った時刻同期は 2022年3月31日 に提供が終了されます。
この期日以降は本記事の方法は使えませんのでご注意ください。

www.atmarkit.co.jp

(以下本題)

基本的にNTPでやれよって話なんですが、NTPでインターネットに出れない環境なんかがあったりしてどうにかならんかと調べてたところ、NICTでWEBサービスとして日本標準時を取得できる様にしてくれてるのを知ったので、これを取得してシステムの現在時刻を更新するPowerShellスクリプトを書いてみました。

書いたスクリプト

こんな感じ。

NICTからJSONで公開されている現在時刻を取得してシステム時刻を更新するスクリプト

NICTの仕様について

www.nict.go.jp

こちらでURLと取得できる情報の詳細が公開されています。
今回のスクリプトではJSONを取得する方式にしています。

スクリプトの中身について

基本的な処理の流れとしては、公開されているURL(http://ntp-a1.nict.go.jp/cgi-bin/json)から現在時刻stの内容を取得し、このstはUnixTimeなので.NETのTicksに変換してからSet-Date関数を使ってシステムの現在時刻を更新しているだけになります。

また、NTPの様に厳密に通信の遅延を計測することができないので単純にJSONを取得するのかかった時間の1/2を遅延とみなして取得した時刻に加算してます。
この様な仕様にしたので通信に時間がかかりすぎた場合はエラー扱いとして処理を中断する様にしています。

その他の方法

HTTPを使って時刻同期を行う方法は結構昔から考えられているみたいで、HTTPヘッダーにある時刻を取得して同期に使う方法がポピュラーっぽいです。

PowerShellだとこんな感じでヘッダーの時刻が取れます。

(Invoke-WebRequest -Uri "http://www.google.co.jp/").Headers.Date

実行結果

Mon, 27 Apr 2015 14:22:35 GMT

あとはこの時刻をパースしてやれば良いだけです。
アクセス先の時刻をどの程度信頼するかってのが微妙なところですが確かにお手軽ではあります。