flake8 plugin which bans the usage of datetime.datetime.utcnow and datetime.datetime.utcfromtimestamp
Project description
flake8-ban-utcnow
flake8 plugin which checks that datetime.utcnow()
and datetime.utcfromtimestamp()
are not used. It suggests using datetime.now(timezone.utc)
and datetime.fromtimestamp(ts, tz=timezone.utc)
instead respectively.
Also, utcnow
and utcfromtimestamp
are finally deprecated in Python 3.12:
- PR: https://github.com/python/cpython/pull/103858
- Issue: https://github.com/python/cpython/issues/103857
note: timezone must be imported from datetime
first:
from datetime import datetime
from datetime import timezone
datetime.now(timezone.utc)
from datetime import datetime
from datetime import timezone
datetime.fromtimestamp(1684079261, tz=timezone.utc)
installation
pip install flake8-ban-utcnow
flake8 code
Code | Description |
---|---|
UTC001 | don't use datetime.datetime.utcnow(), use datetime.datetime.now(datetime.timezone.utc) instead or datetime.now(datetime.UTC) on >= 3.11. |
UTC002 | don't use datetime.datetime.utcfromtimestamp(), use datetime.datetime.fromtimestamp(..., tz=datetime.timezone.utc) instead or datetime.datetime.fromtimestamp(..., tz=datetime.UTC) on >= 3.11. |
as a pre-commit hook
See pre-commit for instructions
Sample .pre-commit-config.yaml
:
- repo: https://github.com/pycqa/flake8
rev: 6.0.0
hooks:
- id: flake8
additional_dependencies: [flake8-ban-utcnow==0.2.0]
rationale
One could expect that when explicitly calling datetime.utcnow()
the datetime
object would be timezone aware, but it's not! A common pitfall is, deriving a
timestamp from the datetime
object created using datetime.utcnow()
.
example
-
the computer is in
CEST
and we want to derive adatetime
in UTC formatted as a timestamp hence callingutcnow().timestamp()
.>>> from datetime import datetime >>> datetime.utcnow() datetime.datetime(2022, 8, 7, 23, 40, 17, 7858) >>> datetime.utcnow().timestamp() 1659908656.048843
-
if we convert the timestamp, it says this, which is obviously incorrect.
GMT: Sunday, 7. August 2022 21:44:16 Your time zone: Sunday, 7. August 2022 23:44:16 GMT+02:00 DST Relative: 2 hours ago
-
converting it using python and
datetime.fromtimestamp
, we by accident get the correct datetime in UTC>>> datetime.fromtimestamp(1659908656.048843) datetime.datetime(2022, 8, 7, 23, 44, 16, 48843)
-
being aware that the timestamp should be in
UTC
we callutcfromtimestamp
instead and get the result as above, since the timestamp actually is in local time, but unaware of this.>>> datetime.utcfromtimestamp(1659908656.048843) datetime.datetime(2022, 8, 7, 21, 44, 16, 48843)
the correct way
-
the computer is in
CEST
and we want to actually derive adatetime
in UTC formatted as a timestamp.>>> from datetime import timezone >>> from datetime import datetime >>> datetime.now(timezone.utc).timestamp() 1659916399.651218
-
we now get what we actually expect
GMT: Sunday, 7. August 2022 23:53:19 Your time zone: Monday, 8. August 2022 01:53:19 GMT+02:00 DST Relative: A few seconds ago
-
the next thing to keep in mind is, that only timezone-aware
datetime
objects can be compared hence using this forces us to always make sure all objects are timezone aware.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Hashes for flake8_ban_utcnow-0.2.0-py2.py3-none-any.whl
Algorithm | Hash digest | |
---|---|---|
SHA256 | b7d9069142ccd96fb1e99c9c892f5c0d03929f6bc94dae58bbabfff27e6510db |
|
MD5 | 7a48d99f0a5f9aa475aaa40260cadc21 |
|
BLAKE2b-256 | 0a2542cbd902af681271dcf990dbaa5df448ea7c89c66ce9d223dcd354a5ebc9 |