urllib3
1from __future__ import annotations
2
3import datetime
4import os
5import time
6import typing
7from contextlib import contextmanager
8
9import pytest
10
11try:
12import zoneinfo
13except ImportError:
14# Python < 3.9
15from backports import zoneinfo # type: ignore[no-redef]
16
17
18@contextmanager
19def stub_timezone_ctx(tzname: str | None) -> typing.Generator[None, None, None]:
20"""
21Switch to a locally-known timezone specified by `tzname`.
22On exit, restore the previous timezone.
23If `tzname` is `None`, do nothing.
24"""
25if tzname is None:
26yield
27return
28
29# Only supported on Unix
30if not hasattr(time, "tzset"):
31pytest.skip("Timezone patching is not supported")
32
33# Make sure the new timezone exists
34try:
35zoneinfo.ZoneInfo(tzname)
36except zoneinfo.ZoneInfoNotFoundError:
37raise ValueError(f"Invalid timezone specified: {tzname!r}")
38
39# Get the current timezone
40old_tzname = datetime.datetime.now().astimezone().tzname()
41if old_tzname is None:
42raise OSError("Cannot determine current timezone")
43
44os.environ["TZ"] = tzname
45time.tzset()
46yield
47os.environ["TZ"] = old_tzname
48time.tzset()
49