I've been having a site problem that I've tracked down to DateTime. Simply enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November. Good Example:
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 GMT-5') print start 2005/10/01 01:00:00 GMT-5 earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/11/01
Bad Example: (Here's the problem)
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 US/Central') print start 2005/10/01 01:00:00 US/Central earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/10/31 23:00:00 US/Central
I've confirmed this occurs with several of the US/ timezones (US/Pacific, US/Alaska, etc) Can anyone help me figure out why the resulting date is coming up 1 hour short of the expected 2005/11/01 ? Thanks! Eric
I've been having a site problem that I've tracked down to DateTime. Simply
enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November.
Good Example:
from DateTime import DateTime>>> start=DateTime('2005/10/01 01:00:00 GMT-
5')>>> print start2005/10/01 01:00:00 GMT-5>>> earlyStart=start.earliestTime()
print earlyStart2005/10/01>>> print earlyStart+312005/11/01
Bad Example: (Here's the problem)
from DateTime import DateTime>>> start=DateTime('2005/10/01 01:00:00 US/Central')>>> print start2005/10/01 01:00:00 US/Central>>> earlyStart=start.earliestTime ()>>> print earlyStart2005/10/01>>> print earlyStart+312005/10/31 23:00:00 US/Central I've confirmed this occurs with several of the US/ timezones (US/Pacific, US/Alaska, etc) Can anyone help me figure out why the resulting date is coming up 1 hour short of the expected 2005/11/01 ? Thanks! Eric <eric@...> writes: Sorry for the oversight...This occurs with zope-2.9.5 and zope-2.9.7 Eric
--On 25. August 2007 07:18:42 -0500 Eric Thomas <eric@thomasfam.com> wrote:
I've been having a site problem that I've tracked down to DateTime. Simply enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November.
Likely because the timezone support is known to be partly broken (since ages). -aj
----- Original Message ----- From: "Eric Thomas" <eric@thomasfam.com> To: <zope@zope.org> Sent: Saturday, August 25, 2007 8:18 AM Subject: [Zope] Help with DateTime.earliestTime()
I've been having a site problem that I've tracked down to DateTime. Simply enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November.
Good Example:
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 GMT-5') print start 2005/10/01 01:00:00 GMT-5 earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/11/01
Bad Example: (Here's the problem)
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 US/Central') print start 2005/10/01 01:00:00 US/Central earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/10/31 23:00:00 US/Central
I've confirmed this occurs with several of the US/ timezones (US/Pacific, US/Alaska, etc)
Can anyone help me figure out why the resulting date is coming up 1 hour short of the expected 2005/11/01 ?
I don't know what your problem is, but here are some code snippets I used to get around a timezone problem I was having: # def custom timezone class class LocalTimezone(datetime.tzinfo): def utcoffset(self, dt): STDOFFSET = datetime.timedelta(seconds = -_time.timezone) ZERO = datetime.timedelta(0) if _time.daylight: DSTOFFSET = datetime.timedelta(seconds = -_time.altzone) else: DSTOFFSET = STDOFFSET if self._isdst(dt): return DSTOFFSET else: return STDOFFSET def dst(self, dt): STDOFFSET = datetime.timedelta(seconds = -_time.timezone) ZERO = datetime.timedelta(0) if _time.daylight: DSTOFFSET = datetime.timedelta(seconds = -_time.altzone) else: DSTOFFSET = STDOFFSET if self._isdst(dt): DSTDIFF = DSTOFFSET - STDOFFSET return DSTDIFF else: return ZERO def tzname(self, dt): return _time.tzname[self._isdst(dt)] def _isdst(self, dt): tt = (dt.year, dt.month, dt.day, dt.hour, dt.minute, dt.second, dt.weekday(), 0, -1) stamp = _time.mktime(tt) tt = _time.localtime(stamp) return tt.tm_isdst > 0 # usage code... Local = LocalTimezone() chkDate = datetime.datetime.now(Local) now = datetime.datetime.now(Local) # see if we have to apply a local timezone offset if tzo: # get the number of hours less than UTC (GMT) localTZO = int(chkDate.strftime('%z')[0:-2]) # make sure we have the target tzo as an integer targetTZO = int(tzo) diffTZO = 0 if targetTZO < localTZO: diffTZO = -(-targetTZO + localTZO) elif targetTZO > localTZO: diffTZO = (-localTZO + targetTZO) if diffTZO: # we have to adjust our dates to account for the time zone difference chkDate = chkDate + datetime.timedelta(hours=diffTZO) now = now + datetime.timedelta(hours=diffTZO) # create a time delta object (a date/time object that is a duration) for 6 months maxDate = datetime.timedelta(weeks=24) # check for events within a 6 month window while chkDate < now + maxDate: This code was just ripped from an application, but may provide you with some ideas for a work-around. Good luck! Jonathan
Eric Thomas wrote at 2007-8-25 07:18 -0500:
I've been having a site problem that I've tracked down to DateTime. Simply enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November.
Good Example:
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 GMT-5') print start 2005/10/01 01:00:00 GMT-5 earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/11/01
Bad Example: (Here's the problem)
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 US/Central') print start 2005/10/01 01:00:00 US/Central earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/10/31 23:00:00 US/Central
I've confirmed this occurs with several of the US/ timezones (US/Pacific, US/Alaska, etc)
This looks like a daytime saving problem: With daytime saving, the clock often is put back for an hour at the last samday in october.... The "DateTime" implementation could avoid this *if* the arithmetic would only accept "int" (then it would be very likely that you only want to modify the day but not hours, minutes and seconds). But the arithmetic accepts "float" and that necessitates some surprises with time discontinuities (such as daytime saving switches).
Can anyone help me figure out why the resulting date is coming up 1 hour short of the expected 2005/11/01 ?
Thanks!
Eric <div>I've been having a site problem that I've tracked down to DateTime. Simply enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November. </div> <div> </div> <div>Good Example:</div> <div> <p>>>> from DateTime import DateTime<br>>>> start=DateTime('2005/10/01 01:00:00 GMT-5')<br>>>> print start<br>2005/10/01 01:00:00 GMT-5<br>>>> earlyStart=start.earliestTime()<br> >>> print earlyStart<br>2005/10/01<br>>>> print earlyStart+31<br>2005/11/01</p></div> <div> <p>Bad Example: (Here's the problem)</p> <p>>>> from DateTime import DateTime<br>>>> start=DateTime('2005/10/01 01:00:00 US/Central')<br>>>> print start<br>2005/10/01 01:00:00 US/Central<br>>>> earlyStart=start.earliestTime ()<br>>>> print earlyStart<br>2005/10/01<br>>>> print earlyStart+31<br>2005/10/31 23:00:00 US/Central</p> <p>I've confirmed this occurs with several of the US/ timezones (US/Pacific, US/Alaska, etc)</p> <p>Can anyone help me figure out why the resulting date is coming up 1 hour short of the expected 2005/11/01 ?</p> <p>Thanks!</p> <p>Eric</p> <p> </p> <p> </p></div>
-- Dieter
Dieter Maurer <dieter@...> writes:
Eric Thomas wrote at 2007-8-25 07:18 -0500:
I've been having a site problem that I've tracked down to DateTime. Simply enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November.
Good Example:
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 GMT-5') print start 2005/10/01 01:00:00 GMT-5 earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/11/01
Bad Example: (Here's the problem)
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 US/Central') print start 2005/10/01 01:00:00 US/Central earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/10/31 23:00:00 US/Central
I've confirmed this occurs with several of the US/ timezones (US/Pacific, US/Alaska, etc)
This looks like a daytime saving problem:
With daytime saving, the clock often is put back for an hour at the last samday in october....
The "DateTime" implementation could avoid this *if* the arithmetic would only accept "int" (then it would be very likely that you only want to modify the day but not hours, minutes and seconds). But the arithmetic accepts "float" and that necessitates some surprises with time discontinuities (such as daytime saving switches).
Can anyone help me figure out why the resulting date is coming up 1 hour short of the expected 2005/11/01 ?
Thanks!
Eric
I've submitted this as a zope bug and I agree that it looks like a daytime saving problem. The problem was tiggered nightly by a Google bot hitting various dates on my site's calendar. Even more interesting is that the seconds, milliseconds, and timezone stored within the DateTime are correct after the addition. So, if I compare the two results from the examples I gave using DateTime.isEqualTo(), the answer is True. This really creates a lot of opportunity for error. To work around this, I've modified the addition so that instead of adding 1 day, it adds 1.5 days. This extra half a day is removed by the theDateTime.earliestTime() call but is enough to overcome the DST addition problem. Ugly hack. Thanks all. - Eric
--On 26. August 2007 19:12:18 +0000 Eric <eric@thomasfam.com> wrote:
Dieter Maurer <dieter@...> writes:
Eric Thomas wrote at 2007-8-25 07:18 -0500:
I've been having a site problem that I've tracked down to DateTime. Simply enough, the code snippets below both try to add 31 days to the first day in October. I'm expecting this to result in the first day of November.
Good Example:
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 GMT-5') print start 2005/10/01 01:00:00 GMT-5 earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/11/01
Bad Example: (Here's the problem)
from DateTime import DateTime start=DateTime('2005/10/01 01:00:00 US/Central') print start 2005/10/01 01:00:00 US/Central earlyStart=start.earliestTime() print earlyStart 2005/10/01 print earlyStart+31 2005/10/31 23:00:00 US/Central
I've confirmed this occurs with several of the US/ timezones (US/Pacific, US/Alaska, etc)
This looks like a daytime saving problem:
With daytime saving, the clock often is put back for an hour at the last samday in october....
The "DateTime" implementation could avoid this *if* the arithmetic would only accept "int" (then it would be very likely that you only want to modify the day but not hours, minutes and seconds). But the arithmetic accepts "float" and that necessitates some surprises with time discontinuities (such as daytime saving switches).
Can anyone help me figure out why the resulting date is coming up 1 hour short of the expected 2005/11/01 ?
Thanks!
Eric
I've submitted this as a zope bug and I agree that it looks like a daytime saving problem. The problem was tiggered nightly by a Google bot hitting various dates on my site's calendar.
Even more interesting is that the seconds, milliseconds, and timezone stored within the DateTime are correct after the addition. So, if I compare the two results from the examples I gave using DateTime.isEqualTo(), the answer is True. This really creates a lot of opportunity for error.
If you can: use Python's datetime module. DateTime is broken in many ways. -aj
Andreas Jung wrote at 2007-8-26 21:23 +0200:
... If you can: use Python's datetime module. DateTime is broken in many ways.
If it handles daytime saving and addition by some float days -- it will not have any chance... If it does not handle daytime saving -- then it misses an essential use case... Some problems come from the complexity of the real world and not from a particular implementation.... -- Dieter
On 8/27/07, Dieter Maurer <dieter@handshake.de> wrote:
Andreas Jung wrote at 2007-8-26 21:23 +0200:
... If you can: use Python's datetime module. DateTime is broken in many ways.
If it handles daytime saving and addition by some float days -- it will not have any chance...
If it does not handle daytime saving -- then it misses an essential use case...
Some problems come from the complexity of the real world and not from a particular implementation....
-- Dieter
In this case it seems that the complexity is being added by the DateTime implementation. When given an int number of days and a DateTime that has no time element, DateTime should not convert everything down to seconds and account for DST that happens to occur during the period. When adding days + days, I'd expect to get a result that only considers days; not DST. So I agree with your earlier post that DateTime should treat int and float addition differently. It should also probably look at the DateTime and revert to integer math if there is no time element present. - Eric
Eric, on 2007-08-26:
To work around this, I've modified the addition so that instead of adding 1 day, it adds 1.5 days. This extra half a day is removed by the theDateTime.earliestTime() call but is enough to overcome the DST addition problem. Ugly hack.
I had the same problem once in the eXtremeManagement Plone product. For a monthly overview I needed to do something for every day of the month. I worked around it with the code below. day = 1 date = DateTime(2007, 10, 1) # 1 October 2007 while True: # skipped some lines irrelevant to the DateTime problem day += 1 try: date = DateTime(self.year, self.month, day) except: break Hm, that should probably be "except DateTime.DateTime.DateError" but there is not really anything else that can go wrong here. -- Maurits van Rees | http://maurits.vanrees.org/ [NL] Work | http://zestsoftware.nl/ "Do not worry about your difficulties in computers, I can assure you mine are still greater."
Maurits van Rees wrote:
Eric, on 2007-08-26:
To work around this, I've modified the addition so that instead of adding 1 day, it adds 1.5 days. This extra half a day is removed by the theDateTime.earliestTime() call but is enough to overcome the DST addition problem. Ugly hack.
I had the same problem once in the eXtremeManagement Plone product. For a monthly overview I needed to do something for every day of the month. I worked around it with the code below.
day = 1 date = DateTime(2007, 10, 1) # 1 October 2007 while True: # skipped some lines irrelevant to the DateTime problem day += 1 try: date = DateTime(self.year, self.month, day) except: break
Hm, that should probably be "except DateTime.DateTime.DateError" but there is not really anything else that can go wrong here.
A ConflictError can go wrong here, which is an additional and important reason not to have a bare except. There are good reasons without that, as well. --jcc -- Connexions http://cnx.org "Building Websites with Plone" http://plonebook.packtpub.com
J Cameron Cooper, on 2007-08-27:
Maurits van Rees wrote:
Hm, that should probably be "except DateTime.DateTime.DateError" but there is not really anything else that can go wrong here.
A ConflictError can go wrong here, which is an additional and important reason not to have a bare except. There are good reasons without that, as well.
Well, you are right of course. I fixed it. Thanks for keeping me sharp. :) -- Maurits van Rees | http://maurits.vanrees.org/ [NL] Work | http://zestsoftware.nl/ "Do not worry about your difficulties in computers, I can assure you mine are still greater."
participants (7)
-
Andreas Jung -
Dieter Maurer -
Eric -
Eric Thomas -
J Cameron Cooper -
Jonathan -
Maurits van Rees