Skip Menu |

Preferred bug tracker

Please visit the preferred bug tracker to report your issue.

This queue is for tickets about the DateTime CPAN distribution.

Report information
The Basics
Id: 104646
Status: resolved
Priority: 0/
Queue: DateTime

People
Owner: Nobody in particular
Requestors: ZHTWN [...] cpan.org
Cc:
AdminCc:

Bug Information
Severity: (no value)
Broken in: (no value)
Fixed in: (no value)



Subject: today() fails when 00:00 is not valid in local time zone
Some time zones, such as Brazil, do the daylight saving time shift at midnight, so 00:00::00 is not a valid time on the day that DST is entered. On these days, the first second of the day is 01:00:00. Thus, when today() tries to truncate to the current day, it fails with the "Invalid local time for date in time zone" error message. Equivalent code, using the day of the DST change time for Brazil: $d = DateTime->new( year => 2014, month => 10, day => 19, time_zone => 'America/Sao_Paulo') The documentation correctly notes that some times are invalid in some time zones, but having today() fail as well is somewhat unexpected. It can cause obscure failures for code that was running fine on any other day. This is a tricky one. At minimum, this should be noted in the documentation. One could argue that today() really means "the first valid moment of the given day", in which case the above example should return 2014-10-19T01:00:00. On the other hand, this may cause surprises for developers that assume that today() will always return a DateTime that's truncated to the day, with all smaller components set to zero. Another exhausting alternative is to rework the whole DateTime system to allow for a "precision" for each DateTime, and consider all components smaller than the given precision to be undefined rather than zero. However, this is a large behavioral change to a key module, which would add to the trickiness. I'm not sure what the best course is for this one...I ended up hacking a local safe_today() method that caught for the "Invalid local time" exception and moved the time one hour in the future.
On Sat May 23 19:18:09 2015, ZHTWN wrote: Show quoted text
> Some time zones, such as Brazil, do the daylight saving time shift at > midnight, so 00:00::00 is not a valid time on the day that DST is > entered. On these days, the first second of the day is 01:00:00. > > Thus, when today() tries to truncate to the current day, it fails with > the "Invalid local time for date in time zone" error message. > > Equivalent code, using the day of the DST change time for Brazil: > > $d = DateTime->new( year => 2014, month => 10, day => 19, time_zone => > 'America/Sao_Paulo') > > The documentation correctly notes that some times are invalid in some > time zones, but having today() fail as well is somewhat unexpected. It > can cause obscure failures for code that was running fine on any other > day. > > This is a tricky one. At minimum, this should be noted in the > documentation. > > One could argue that today() really means "the first valid moment of > the given day", in which case the above example should return 2014-10- > 19T01:00:00. On the other hand, this may cause surprises for > developers that assume that today() will always return a DateTime > that's truncated to the day, with all smaller components set to zero. > > Another exhausting alternative is to rework the whole DateTime system > to allow for a "precision" for each DateTime, and consider all > components smaller than the given precision to be undefined rather > than zero. However, this is a large behavioral change to a key module, > which would add to the trickiness. > > I'm not sure what the best course is for this one...I ended up hacking > a local safe_today() method that caught for the "Invalid local time" > exception and moved the time one hour in the future.
There isn't really a great way to fix this. That said, if you're calling today() because all you care about it is the date and you can ignore times, then you should use the floating time zone. This will avoid lots of time-related issues that are irrelevant if you're just doing date-only math.