ASP.NETでタイムゾーンを使用する方法
質問
「オンラインリマインダーシステム」に取り組んでいます。プロジェクト(ASP.NET 2.0(C#)/ SQL Server 2005)
これは、特定の日付にメールをユーザーに送信するリマインダーサービスです。しかし、問題はユーザーが特定の国から来たのではなく、世界中の異なるタイムゾーンから来ているということです。今、私が登録するとき、私はWindowsがインストール時に私たちのタイムゾーンを尋ねるのと同じ方法でユーザーのタイムゾーンを求めています。
しかし、ユーザーが(+5.30)またはタイムゾーンを選択した場合、asp.netアプリケーションでこのタイムゾーンを処理する方法はわかりません。タイムゾーンに従って作業する方法。
そして、このアプリケーションでタイムゾーンを処理するより良い方法があるかどうか提案してください??
ありがとう
解決
まず、データがどのタイムゾーンにあるかを確認します。保存するDateTimeはすべてUTC時間で保存することをお勧めします( DateTime.ToUniversalTime()
を使用して、それをつかむ)。
ユーザーにリマインダーを保存する場合、現在のUTC時間を必要とし、ユーザーのタイムゾーンの差を追加または削除し、その新しい時間をUTCに変換します。これは、DBに保存するものです。
その後、送信するリマインダーを確認する場合は、UTC時間に従って、今すぐ送信するリマインダーをデータベースで確認するだけです。基本的に、 DateTime.Now.ToUniversalTime()
の前にあるタイムスタンプを持つすべてのアラームを取得します。
更新:いくつかの実装の詳細:
TimeZoneInfo.GetSystemTimeZones()
メソッドからタイムゾーンのリストを取得できます。これらを使用して、ユーザーのタイムゾーンのリストを表示できます。選択したタイムゾーンの Id
プロパティを保存する場合、そこからTimeZoneInfoクラスインスタンスを作成し、特定のローカル日付/時刻値のUTC時間を計算できます。
TimeZoneInfo tzi = TimeZoneInfo.FindSystemTimeZoneById("<the time zone id>");
// May 7, 08:04:00
DateTime userDateTime = new DateTime(2009, 5, 7, 8, 4, 0);
DateTime utcDateTime = userDateTime.Subtract(tzi.BaseUtcOffset);
他のヒント
サーバー側で常に( UTC(GMT)時間を使用する(コードビハインド、データベースなど)を使用し、表示のためにUTCから現地時間に時間を変換することをお勧めしますのみ。つまり、データベースでの時間の節約、計算の実行など、すべての時間操作はUTCを使用して実行する必要があります。
問題は、コードビハインドがクライアントブラウザーのタイムゾーンをどのように認識するかです。ユーザーがフォームに日付/時刻の値( 12/30/2009 14:30 など)を入力し、サーバーに送信するとします。ユーザーが現地時間を送信したと仮定すると、サーバーはこの値をUTCに変換する方法をどのように知るのですか?
アプリケーションは、ユーザーにタイムゾーンの指定(および永続的なCookieまたはデータベースへの保存)を求めることができますが、ユーザーの追加の努力が必要であり、アプリはこのためのロジックと画面を実装する必要があります。アプリがクライアントのタイムゾーンを自動的に決定することができればもっといいでしょう。
JavaScriptの getTimezoneOffset 関数を使用してこの問題に対処しました。クライアントの現地時間とGMTの時間差をサーバーに伝えることができるAPIのみ。これはクライアント側のAPIであるため、次のことを行いました。サーバー側で、タイムオフセット値を保持するカスタムセッションCookieを確認し、使用できない場合はページをリロードします(POSTではなくGET呼び出し中のみ)タイムオフセットを生成してCookieに保存するJavaScriptロジックが追加されています。クライアント側からは、これはほとんど透過的です(セッション中にGETでページをリロードします)。 Cookieにオフセットを取得したら、時間変換の方向(UTCから現地時間、または現地時間からUTC)に応じて時間管理機能に適用します。
これは少し複雑に聞こえるかもしれませんが、ヘルパー関数を作成した後、この機能をサイトに統合するには、Page_Load(時間を必要とするページの)で単一呼び出し変換)、およびブラウザとの間で時間値を送受信するときに時間変換ルーチンを使用します。使用方法の例を次に示します。
using My.Utilities.Web;
...
// Derive the form class from BaseForm instead of Page.
public class WebForm1: BaseForm
{
...
private void Page_Load(object sender, System.EventArgs e)
{
// If we only want to load the page to generate the time
// zone offset cookie, we do not need to do anything else.
if (InitializeLocalTime())
return;
// Assume that txtStartDate is a TextBox control.
if (!IsPostback)
{
// To display a date-time value, convert it from GMT (UTC)
// to local time.
DateTime startDate = GetStartDateFromDB(...);
txtStartDate.Text = FormatLocalDate(startDate);
...
}
else
{
// To save a date-time value, convert it from local
// time to GMT (UTC).
DateTime tempDate = DateTime.Parse(txtStartDate.Text);
DateTime startDate = ConvertLocalTimeToUtc(tempDate);
SaveStartDateInDB(startDate, ...);
...
}
}
...
}
詳細が必要な場合は、時間について:ASP.NETアプリケーションでの時間のローカライズ記事(申し訳ありませんが、asp.netPROは有料購読者のみへのアクセスを制限しているため、出版社のサイトには直接リンクがありません。PDFコピーへのリンクがあります。しかし)。記事からサンプルを投稿できればいいのですが、著作権を侵害したくありません。ただし、すべての必要な機能とドキュメントを備えたヘルパーライブラリを構築するプロジェクトです。 (不要なものは無視してください)。
更新:この記事は、新しい出版社こちらによってサンプルプロジェクトとともにオンラインで投稿されました。 a>。
これまでのすべての回答の問題は、Prashantが達成しようとしていることを考慮していないことです。夏時間の変更の前日にシステムのユーザーが+12のオフセットを持ち、翌日のリマインダーを設定する場合、リマインダーがトリガーされるはずのユーザーのオフセットは+13になります。
そのため、現在発生していることに対してのみ現在のオフセットを使用できます。私は他のすべての人に同意しますが、常にサーバー側(表示のみに使用されるものを除く)はUTCで保存する必要があります。
DateTimeOffset の使用をご覧ください。フレームワーク2.0以降を使用している場合は、DateTimeではなく構造体。
DateTimeOffsetはUTC時間を基準とした特定の時点を表すため、この場合は作業しやすいはずです。
2つのステップがあります:
-
Javascriptを使用してクライアント側で異なるタイムゾーンを検出します:
var dt = new Date(); var diffInMinutes = -dt.getTimezoneOffset();
-
次に、サーバー側で、上記の検出されたタイムゾーンオフセットに基づいてサーバー時間をクライアント時間に変換するC#コード:
------------------------;
string queryStr = Request.QueryString["diffInMinutes"];
int diffInMinutes = 0;
if (Int32.TryParse(queryStr, out diffInMinutes))
{
clientTime = serverTime.ToUniversalTime().AddMinutes(diffInMinutes);
}
基本的に、ユーザーが入力した現地時間にオフセット(時間+分)を追加するだけです。オフセットを追加すると、基本的にUTC(基本的にはGMT)タイムゾーンのDateTimeが得られます。
通常、すべての時間をUTCに標準化するのが最も簡単です。これにより、アプリケーションロジックがオフセットを処理する必要がなくなります。
このページにはいくつかの良い例があります: http://msdn.microsoft .com / en-us / library / bb546099.aspx
問題は、UTCからのオフセットが1年の異なる時期に異なることです。各タイムゾーンには独自のルールがあります。 (会議室のスケジュールアプリを開発するときに、この難しい方法を学びました。)
組み込みサポートがあるように見えます: http ://msdn.microsoft.com/en-us/library/system.timezoneinfo.converttime.aspx
自分で試したことはありませんが、夏時間を考慮した正しい変換が約束されているようです。
そうでない場合、私が使用した(価格の高い)商用ツールは次のとおりです。 http://www.worldtimeserver .com / time_zone_guide /