In over 20 years of using python I have found this issue, in its various
manifestations, to be the biggest source of confusion for people with
datetime module.

On Thu, 30 Dec 2021 at 18:22 Brock Mendel <[email protected]> wrote:

> FWIW the proximate reason for bumping this thread is an issue reported to
> pandas caused by a user confused by datetime.utcnow().timestamp() behavior
> https://github.com/pandas-dev/pandas/issues/45054
>
> I guess there's a couple of empirical questions here:
> 1) How common is this type of confusion?
> 2) How common is the utcnow().strftime() or utcnow().isoformat() usage
> where changing/deprecating would make a real perf/brevity difference?
>
>
> On Thu, Dec 30, 2021 at 2:19 AM Oren Tirosh <[email protected]> wrote:
>
>> Since changing datetime would break compatibility, I experimented with a
>> module called adatetime ('a' for aware) where timezone-naive objects are
>> not allowed.
>>
>> The class methods adatetime.datetime.fromtimestamp(t) and
>> adatetime.datetime.utcfromtimestamp(t) produces objects that compare as
>> equal. One is in the local timezone and the other is in UTC but they
>> represent the same point in time. With the standard datetime module this
>> results in unequal naive objects.
>>
>> There is no such thing as a local time_t in POSIX. Internal
>> representation is always UTC and broken-down human time (struct tm) always
>> has an associated timezone. No mixups. The python datetime module supports
>> a non-UTC int or float representation with the methods .fromtimestamp(),
>> .utcfromtimestamp() and .timestamp(). In these methods the time in seconds
>> may be implicitly treated or generated as local time. I consider this the
>> "Original Sin" of an otherwise very well-designed module.
>>
>> I experimented with various alternatives for how adatetime should behave
>> when tzinfo is not provided: using either UTC or the local timezone as
>> default or always require it to be passed explicitly. I think the best
>> default is UTC, with a singleton named 'local' that can be passed as tzinfo
>> to specify using the local timezone (same behavior as adding
>> .astimezone(None)). For code that always passes an explicit tzinfo this
>> makes adatetime almost 100% compatible to the standard datetime. The only
>> difference is the behavior of .fromtimestsamp() / .utcfromtimestamp() being
>> aware by default. To make it fully compatible would require either adding
>> some new method for creating aware datetime to both datetime and adatetime
>> or removing .utcfromtimestamp() from adatetime and making adatetime's
>> .fromtimestamp() tzinfo argument not optional.
>>
>>
>> On Tue, 28 Dec 2021 at 04:24, Paul Ganssle <[email protected]> wrote:
>>
>>> I don't really think zoneinfo being in the stdlib has much bearing on
>>> the question of utcnow/utctimestamp. We already had a UTC object in the
>>> standard library, and could have made this change any time, but chose not
>>> to because it would break backwards compatibility.
>>>
>>> I'm definitely more in favor of deprecating it than I am of changing the
>>> behavior, which would be a major breaking change and one that is hard to
>>> warn about. Removing utcnow would probably be a lot of work for a lot of
>>> people, but many people are probably using it wrong anyway so that may be a
>>> net benefit.
>>>
>>> That said, there is at least one use case I'm concerned about where the
>>> replacement is not great:
>>>
>>> If you want a datetime in UTC that you *immediately format*, attaching
>>> the `UTC` object rather than using `utcnow` would lead to a performance
>>> regression without any actual benefit (and sometimes it's actually a bit of
>>> a pain). For example:
>>>
>>>     print(datetime.utcnow().strftime("%Y-%m-%d %H:%M:%S"))
>>>     print(datetime.utcnow().isoformat())
>>>
>>> would have to turn into:
>>>
>>>     print(datetime.now(UTC).strftime("%Y-%m-%d %H:%M:%S"))
>>>     print(datetime.now(UTC).replace(tzinfo=None).isoformat())
>>>
>>> The first of these is slower but no safer than the `utcnow` version, and
>>> the second of these actually involves stripping the UTC object from the
>>> result of `now` just to avoid `isoformat`'s behavior where it automatically
>>> appends the time zone offset to aware datetimes.
>>>
>>> I haven't looked at it, but it may be that we can special-case
>>> `datetime.timezone.utc` in the `now()` and `fromtimestamp()` constructors
>>> so that `datetime.now(timezone.utc)` is just as fast as
>>> `datetime.utcnow()`, in which case the first example is not a huge deal,
>>> and maybe the second performance regression isn't so bad that it is worth
>>> leaving around footguns like this. It'd be nice to put some numbers on that.
>>>
>>> Best,
>>> Paul
>>> On 12/27/21 19:33, Brock Mendel wrote:
>>>
>>> Now that zoneinfo is in the stdlib, I'd like to revisit the idea of
>>> either a) making utcnow/utcfromtimestamp return tzaware or b) deprecating
>>> in favor of explicitly passing tzinfos to now/fromtimestamp.
>>>
>>> Thoughts?
>>>
>>> On Mon, Apr 22, 2019 at 10:54 AM Alexander Belopolsky <
>>> [email protected]> wrote:
>>>
>>>> > what if I'm in New York, but running on a JupyterLab system in Los
>>>> Angeles?
>>>>
>>>> In this case, it would be the responsibility of the JupyterLab
>>>> designers to set the timezone of the kernel to something useful to the
>>>> user.  In the case of a single-user kernel that would be the user's
>>>> timezone, in the case of multi-user kernels - most likely UTC or something
>>>> that the users can agree upon.  The location of the JupyterLab server
>>>> should never be a consideration.
>>>>
>>>> Setting the timezone is currently more complicated than it should be:
>>>>
>>>> import sys, time
>>>> sys.environ['TZ'] = 'America/New_York'
>>>> time.tzset()
>>>>
>>>> but I don't think we can improve that before python gets an integrated
>>>> timezone database.  For now, this is what you should do to make sure a
>>>> remote system uses the timezone that you want.
>>>> _______________________________________________
>>>> Datetime-SIG mailing list -- [email protected]
>>>> To unsubscribe send an email to [email protected]
>>>> https://mail.python.org/mailman3/lists/datetime-sig.python.org/
>>>> The PSF Code of Conduct applies to this mailing list:
>>>> https://www.python.org/psf/codeofconduct/
>>>>
>>>
>>> _______________________________________________
>>> Datetime-SIG mailing list -- [email protected]
>>> To unsubscribe send an email to 
>>> [email protected]https://mail.python.org/mailman3/lists/datetime-sig.python.org/
>>> The PSF Code of Conduct applies to this mailing list: 
>>> https://www.python.org/psf/codeofconduct/
>>>
>>> _______________________________________________
>>> Datetime-SIG mailing list -- [email protected]
>>> To unsubscribe send an email to [email protected]
>>> https://mail.python.org/mailman3/lists/datetime-sig.python.org/
>>> The PSF Code of Conduct applies to this mailing list:
>>> https://www.python.org/psf/codeofconduct/
>>>
>> _______________________________________________
>> Datetime-SIG mailing list -- [email protected]
>> To unsubscribe send an email to [email protected]
>> https://mail.python.org/mailman3/lists/datetime-sig.python.org/
>> The PSF Code of Conduct applies to this mailing list:
>> https://www.python.org/psf/codeofconduct/
>>
>
_______________________________________________
Datetime-SIG mailing list -- [email protected]
To unsubscribe send an email to [email protected]
https://mail.python.org/mailman3/lists/datetime-sig.python.org/
The PSF Code of Conduct applies to this mailing list: 
https://www.python.org/psf/codeofconduct/

Reply via email to