Is modifying System.DateTime reasonable for a Time Zone/Offset aware DateTime object?


So, in my previous “Designing Time Zone Conversion” post, a few readers asked whether we can update System.DateTime to understand Time Zones.


Before we look into whether we can update DateTime, we should look into how this “improved” DateTime should function. Users want a class that can specified a specific point in time. Some users had asked for a DateTime that acutally understands Time Zone. i.e. it is permanently associated with a Time Zone and applies the Time Zone rules as it changes, other users wants a DateTime that has an offset to UTC (i.e. not mapped to a Time Zone). Both feature requests are really asking for the same thing. A DateTime class that describe a particular point in time. Currently, DateTime can describe a particular point in time.. that is if you are describing it in UTC or in your local time zone. However, UTC is hard for people to work with; people do not think of their time in UTC. Only working in your local time zone is difficult too. Technology has basically shrunk the globe. People are attending meeting all over the world, or doing it over technologies like Live Meeting. Now, to design this new class let’s look at the basic requirements:


– able to describe a single point in time unambiguously
– display the time in UTC, Local or other Time Zone or Offset.
– support functionality available in DateTime


Now, what about other scenarios that DateTime used to support? For example, describe a “date” with no time association or describe a “time” with no date associations. What if you don’t know the time zone or offset? You just want to say “I have this Date and Time”, sometimes you’ll be working with a legacy application and they produce date time with no time zone associated with it. You need to be able to specify an “unspecified” Time Zone/Offset then. Now, how should this new DateTime object work between the two modes (“have a specific point in time” vs “not having it”?) How do you convert between the two modes? Would having 2 modes in one type be a good thing or would that just confuse users. If we have two modes, shouldn’t we just have two objects? Since the two objects cannot easily interrop between each other?


These are just some consideration we have to consider before deciding whether we should make a breaking change and modify System.DateTime. Yes…. measuring how much we’ll have to break is another consideration. Making DateTime be TimeZone/Offset aware will be a breaking change. What does DateTime.Kind means then? How should it act? How should the Add/Subtract functionality behave, what about Parse and ToString….etc. We need to ask these questions to each and every API DateTime support.


What do you think? Do you think it even make sense to update DateTime? How much “breaking” will you tolerate so that we modify DateTime to have this support?

Comments (11)

  1. me says:

    You should mention these links for reference:

    http://blogs.msdn.com/bclteam/archive/2004/05/21/136918.aspx

    http://blogs.msdn.com/bclteam/archive/2004/06/01/145487.aspx

    I want DateTime to always, without exception, be in UTC.

    Yes, it will be a lot of work to fix now, but it is always a lot of work to work around the current implementation, too.

    (Yes, I know that I can manually specify it myself in 2.0.)

    Please create an IDateTime interface and make DateTime implement it. Then modify the signatures to use IDateTime.

    That way I can replace your type with my own UTC DateTime class. Also, it will give you more room for future changes, maybe even replacing the entire type someday.

    You really should replace it someday. At least give yourself some room to work.

    Assuming it’s already in UTC, computing the timezone offset manually isn’t too difficult. But having it built in would be useful.

    (Do not confuse time zone and daylight savings.)

    DateTime has always been broken. Break it as much as needed to help fix it.

  2. MichaelGiagnocavo says:

    Breaking DateTime? Can’t this be achieved through a real TimeZone class that can convert? You can’t very well embed timezone information into an 8 byte structure, I don’t think. Changing it would kill DB support, so that’s a rather impractical approach, no? Just make a separate class and let people track timezone separately from the ticks since 1-1-0001 (or however it’s measured). Last thing we need is a bunch of DateTime struct automagic conversion going on.

  3. Damien Guard says:

    I’m with Michael on this in that DateTime should remain as is.

    Perhaps what is needed is a ZonedDateTime class that wraps DateTime and a region/offset indicator.

    When somebody does zonedDateTime1.Subtract(zonedDateTime2) the class could do something like;

    public class ZonedDateTime {

    public DateTime LocalDateTime;

    public Decimal HourOffsetFromUTC;

    public ZonedDateTime(DateTime localDateTime, Decimal hourOffsetFromUTC) {

    LocalDateTime = localDateTime;

    hourOffsetFromUTC = hourOffsetFromUTC;

    }

    public DateTime UTCDateTime {

    get { return LocalDateTime.AddHours(HourOffsetFromUTC); }

    }



    public Subtract(ZonedDateTime otherDateTime) {

     DateTime newDateTime = UTCDateTime.Subtract(otherDateTime.UTCDateTime).Subtract(HourOffsetFromUTC);

     return new ZonedDateTime(newDateTime, HourOffsetFromUTC);

    }

    }

    The only changes then needed to DateTime might be to pop out a ZonedDateTime class – i.e. nothing breaking.

    [)amien

  4. KathyKam says:

    My last post was about investigating on how to improve on System.TimeZone so that we have better support for all the time zones. The comments left by users in that post asked for a DateTime that understands Time Zone, that why I thought this is worth discussing about.

    I agree with you guys that the first problem is with System.TimeZone. However, does System.DateTime needs to be fixed as well?

  5. Michael Giagnocavo says:

    No, DateTime is fine (well, it was until the Kind enum was added…). Just like System.Drawing.Point doesn’t specify a coordinate system, I don’t see why DateTime needs to specify a timezone. The application should be responsible for ensuring it has the right context (for instance, all my server apps record everything in UTC).

    I’m terrified of what would happen if time zone conversion gets tacked on to DateTime in order to make it automatic and easy for some developers. Seriously. I think it’s going to be near impossible to get an acceptable middle ground (i.e., lets ‘enterprise’ devs get magical time zone support, but is flexible and explicit for app devs), that I’d prefer if the BCL team didn’t touch DateTime: "Put the ulong down and nobody gets hurt."

    Suppose there was a reference to a timezone tacked onto datetime. How would this work as soon as that datetime is saved to a DB (or sent pretty much anywhere else)? It’ll get lost and we’ll be in worse position. I think it’s far preferable to make people realise what they’re doing (dealing with timezones) and make them store a timezone separately. It might sound like a lot more work at first, but in the end devs are better off, since that forces them to actually think a bit about time[zones] rather than ship code that "works on their machine" but starts breaking down when timezone usage actually comes into play…

  6. grauenwolf says:

    I really need  time zone information. I deal with multiple time zones all the time. The database is in Pacific Time, the display is usually in Eastern Time, and who knows what time zone our various partner companies and incoming data feeds are using this week.

    Because we deal in bond trades, we have to report time down to the minute. A small error that makes a 3pm trade look like it booked at 5pm could result in thousands of dollars in fines.

    I think you should just create a DateTimeZone class.  Make it a new type is it is clear when we have time zone information and when we don’t.

    The new property on DateTime was a nasty surprise. It didn’t solve anything for me because I need non-local time, and it intoduced bugs because the slightly different semantics.

  7. me says:

    grauenwolf,

    Why do you record the time in Pacific Time?

    Your situation sounds ideal for UTC.

    Store everything in UTC, and only at presentation time offset the value to whatever timezone your user is at.

    While Microsoft could make it a little easier, the offset calculations could hardly be any easier to calculate manually.

    I treat any non-UTC DateTime as a bug.

  8. Strongly agree with those in favor of UTC. Your application should never ever ever store a non-UTC DateTime. If you need to display a DateTime to a user, you can do the conversion at runtime to display to the user – but never store a non-universal time and never transmit a non-universal time out of the process.

    Brilliant analogy to Point. I couldn’t have said it better.

  9. Kathy Kam says:

    Didn’t I say it two weeks ago that API naming is the most difficult thing? 🙂 My BCL post on System.TimeZone2