web-dev-qa-db-ja.com

Azure Web AppsでのTimeZoneの変更DateTimeOffset.Nowでは機能しませんか?

Accordingtomultiplepostings 、Microsoftはアプリケーション設定を使用する機能を有効にしました--WEBSITE_TIME_ZONE --to Webサーバーのタイムゾーンを制御します。

これを試すために、この値をローカルタイムゾーンである「東部標準時」に設定しました。

ASP.NET MVC Razorページで、次のコードを追加しました。

DateTime.Now: @DateTime.Now
DateTimeOffset.Now: @DateTimeOffset.Now
DateTime.UtcNow: @DateTimeOffset.UtcNow

昨夜、東部標準時の午後5:10:07に実行すると、次の出力が得られました。

DateTime.Now: 6/18/2015 5:10:07 PM
DateTimeOffset.Now: 6/18/2015 5:10:07 PM +00:00
DateTime.UtcNow: 6/18/2015 9:10:07 PM

ご覧のとおり、この設定により、DateTime.Nowは、Azure Webサイト/ Webアプリが通常行うようにUTCではなく、私のタイムゾーンで正しい値を返すことができました。 DateTime.UtcNowは、明らかな理由で常に正しい値を返してきました。

ただし、DateTimeOffset.Nowは現地時間を返しますが、オフセットは+00:00で、タイムゾーンではなく時計が変更されたかのようになります。これは、 documentation が(私の強調)と言っていても発生します。

現在のコンピューターの現在の日付と時刻に設定されているDateTimeOffsetオブジェクトを取得します。オフセットは協定世界時(UTC)からの現地時間のオフセットに設定されます

では、WEBSITE_TIME_ZONE設定がDateTime.Nowに影響を与えるが、DateTimeOffset.Nowには影響を与えないということはどうなっているのでしょうか?そして、それを回避する方法はありますか?

明確にするために、サーバーのタイムゾーンを変更したくありません。適切なタイムゾーンに依存しないソリューションに取り組んでいます。しかし、なぜこれがそのように起こるのか、私はまだ興味があります。

17
Tim

私にとっては、今は機能します。動作しない場合は、正しい値を設定してください

  1. レジストリを開く
  2. 「タイムゾーン」を検索する
  3. ゾーンがどのように記述されているかを確認してください。たとえば、私のゾーンは「Eastern EST(+2)」であり、レジストリではその名前は「E. EuropeStandardTime」です。

そこで、Azureアプリのアプリ設定に追加しました"WEBSITE_TIME_ZONE: E. Europe Standard Time"そしてそれは動作します。

5

この質問に出くわした人のために。これは長い間修正されています。

3
Ivan Zlatev

私は同じ問題に直面しています。残念ながら、私は東部標準時に特別に作成された多くのレガシーコードを継承したため、UTCで動作するように更新することは基本的にオプションではありません。

CLRコードを掘り下げた後、ローカルタイムゾーンがシステムレジストリに対して検索されていることが原因のようです。 Azure Web Appsは共有VMで実行されるため、CLRコードを変更せずにこれを適切にサポートする方法がわかりません。

とりあえず、サイトの起動時に次のリフレクションハックを使ってこれを回避し、.Netをだまして東部標準時だと思わせます。これは優れたソリューションではなく、TimeZoneInfoクラスの実装を変更すると機能しなくなる可能性がありますが、変更する理由はこの問題に対処するためです。

// rewrite local timezone
var tz = TimeZoneInfo.FindSystemTimeZoneById("Eastern Standard Time");

var fInfo = typeof(TimeZoneInfo).GetField("s_cachedData", BindingFlags.Static|BindingFlags.NonPublic);
var cachedData = fInfo.GetValue(null);

fInfo = cachedData.GetType().GetField("m_localTimeZone", BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);
fInfo.SetValue(cachedData, tz);
0
Kam Jim