diff options
| author | Rapptz <[email protected]> | 2021-04-04 23:54:08 -0400 |
|---|---|---|
| committer | Rapptz <[email protected]> | 2021-04-04 23:54:08 -0400 |
| commit | ff7094ce9602bad0b4408761841fa02bdb908987 (patch) | |
| tree | d0d37067183f6827398181e598133146f870fa26 /discord/utils.py | |
| parent | Remove some lingering userbot classes in the documentation (diff) | |
| download | discord.py-ff7094ce9602bad0b4408761841fa02bdb908987.tar.xz discord.py-ff7094ce9602bad0b4408761841fa02bdb908987.zip | |
Convert datetimes to aware datetimes with UTC.
Naive datetimes will now be interpreted as local time throughout
the library.
Diffstat (limited to 'discord/utils.py')
| -rw-r--r-- | discord/utils.py | 48 |
1 files changed, 33 insertions, 15 deletions
diff --git a/discord/utils.py b/discord/utils.py index dc8e39f2..3a8002c1 100644 --- a/discord/utils.py +++ b/discord/utils.py @@ -25,6 +25,7 @@ DEALINGS IN THE SOFTWARE. import array import asyncio import collections.abc +from typing import Optional, overload import unicodedata from base64 import b64encode from bisect import bisect_left @@ -103,9 +104,17 @@ class SequenceProxy(collections.abc.Sequence): def count(self, value): return self.__proxied.count(value) -def parse_time(timestamp): +@overload +def parse_time(timestamp: None) -> None: + ... + +@overload +def parse_time(timestamp: str) -> datetime.datetime: + ... + +def parse_time(timestamp: Optional[str]) -> Optional[datetime.datetime]: if timestamp: - return datetime.datetime(*map(int, re.split(r'[^\d]', timestamp.replace('+00:00', '')))) + return datetime.datetime.fromisoformat(timestamp) return None def copy_doc(original): @@ -168,7 +177,7 @@ def oauth_url(client_id, permissions=None, guild=None, redirect_uri=None, scopes return url -def snowflake_time(id): +def snowflake_time(id: int) -> datetime.datetime: """ Parameters ----------- @@ -178,25 +187,34 @@ def snowflake_time(id): Returns -------- :class:`datetime.datetime` - The creation date in UTC of a Discord snowflake ID.""" - return datetime.datetime.utcfromtimestamp(((id >> 22) + DISCORD_EPOCH) / 1000) + An aware datetime in UTC representing the creation time of the snowflake. + """ + timestamp = ((id >> 22) + DISCORD_EPOCH) / 1000 + return datetime.datetime.utcfromtimestamp(timestamp).replace(tzinfo=datetime.timezone.utc) -def time_snowflake(datetime_obj, high=False): +def time_snowflake(dt: datetime.datetime, high: bool = False) -> int: """Returns a numeric snowflake pretending to be created at the given date. - When using as the lower end of a range, use ``time_snowflake(high=False) - 1`` to be inclusive, ``high=True`` to be exclusive - When using as the higher end of a range, use ``time_snowflake(high=True)`` + 1 to be inclusive, ``high=False`` to be exclusive + When using as the lower end of a range, use ``time_snowflake(high=False) - 1`` + to be inclusive, ``high=True`` to be exclusive. + + When using as the higher end of a range, use ``time_snowflake(high=True) + 1`` + to be inclusive, ``high=False`` to be exclusive Parameters ----------- - datetime_obj: :class:`datetime.datetime` - A timezone-naive datetime object representing UTC time. + dt: :class:`datetime.datetime` + A datetime object to convert to a snowflake. + If naive, the timezone is assumed to be local time. high: :class:`bool` Whether or not to set the lower 22 bit to high or low. - """ - unix_seconds = (datetime_obj - type(datetime_obj)(1970, 1, 1)).total_seconds() - discord_millis = int(unix_seconds * 1000 - DISCORD_EPOCH) + Returns + -------- + :class:`int` + The snowflake representing the time given. + """ + discord_millis = int(dt.timestamp() * 1000 - DISCORD_EPOCH) return (discord_millis << 22) + (2**22-1 if high else 0) def find(predicate, seq): @@ -374,12 +392,12 @@ async def sleep_until(when, result=None): ----------- when: :class:`datetime.datetime` The timestamp in which to sleep until. If the datetime is naive then - it is assumed to be in UTC. + it is assumed to be local time. result: Any If provided is returned to the caller when the coroutine completes. """ if when.tzinfo is None: - when = when.replace(tzinfo=datetime.timezone.utc) + when = when.astimezone() now = datetime.datetime.now(datetime.timezone.utc) delta = (when - now).total_seconds() while delta > MAX_ASYNCIO_SECONDS: |