Domanda

Just to give an overview of my project, I have an ASP.NET WebForm application that allows users to log in and schedule an event. The event handling is handled and dispatched by a local Windows server for which I wrote a Windows Service for.

Everything is working fine, except I have some clients who log in from the east coast and some from the west coast.

Can someone please suggest a possible workflow for how I can handle time zone differences? Time zone information is already being stored in the database with each client. I am just confused on how to apply the time zone info.

I know DateTime has a ToUniversalTime() method but it confuses me on how it works because it would almost seem that it would need to know what time zone the DateTime structure is in to be able to convert it into universal time and as far as I know, a DateTime structure does not have timezone info built right into the structure.

Can someone please explain this to me?

È stato utile?

Soluzione

If the event is scheduled to occur once, it would make sense to store it as a DateTimeOffset, or UTC DateTime. If you store it as a DateTimeOffset, you can still display it to the user with the relevant offset - and indeed you can display it to people in other time zones either as their local time, or as the original user's local time with an indicator that it's not the same as the viewer's local time (if you see what I mean).

If it's recurrent (e.g. "4am every day") then that won't be enough, as it won't take account of DST changes. Instead, you should store the local time, and a time zone identifier. See TimeZoneInfo.Id and TimeZoneInfo.FindSystemTimeZoneById.

As a blatant plug, you may wish to look into using the Noda Time API as a rather more expressive alternative to the built-in types...

You should almost certainly not be using DateTime.ToUniversalTime(), as that uses the system time zone (i.e. at your server), which should almost certainly be irrelevant.

Altri suggerimenti

From MSDN:

The ToUniversalTime method converts a DateTime value from local time to UTC. To convert the time in a non-local time zone to UTC, use the TimeZoneInfo.ConvertTimeToUtc(DateTime, TimeZoneInfo) method. To convert a time whose offset from UTC is known, use the ToUniversalTime method.

Starting with the .NET Framework version 2.0, the value returned by the ToUniversalTime method is determined by the Kind property of the current DateTime object.

The default value of Kind on a DateTime is unspecified, so your date will be assumed to be local time.

We have been working on a similar application. We store the TimeZoneOffset and Scheduled Time in a database table. On the client side, the TimeZOneOffset (in minutes) takes into account daylight savings time. It is calculated as follows:

    Dim localZone As TimeZone = TimeZone.CurrentTimeZone 
    Dim StartTime As DateTime = UserEnteredStartDateTime 'from your web app
    Dim TimeZoneOffset As Integer = localZone.GetUtcOffset(StartTime).TotalMinutes

The stored procedure on the server includes a where clause that selects rows that are within the scheduled start time plus a 30 second window as follows:

SELECT Invitations.ID, Invitations.OrganizerName, Invitations.OrganizerEmail, Invitations.EMailBody, Invitations.[Subject]
FROM Invitations 
WHERE (Invitations.MailSent=0) 
And (Invitations.SendTime Between DateAdd(mi,Invitations.TimeZOneOffset,GETUTCDATE()) 
And DateAdd(s,(Invitations.TimeZoneOffset*60)+30,GETUTCDATE())) 
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top