diff --git a/newsfragments/3322.deprecated.txt b/newsfragments/3322.deprecated.txt new file mode 100644 index 000000000..0e1b69f32 --- /dev/null +++ b/newsfragments/3322.deprecated.txt @@ -0,0 +1 @@ +Implement ``bool(trio.Event)`` and have it raise a `DeprecationWarning` and tell users to use `trio.Event.is_set` instead. This is an alternative to ``mypy --enable-error-code=truthy-bool`` for users who don't use type checking. diff --git a/src/trio/_sync.py b/src/trio/_sync.py index ca373922b..d026f4bc3 100644 --- a/src/trio/_sync.py +++ b/src/trio/_sync.py @@ -1,7 +1,7 @@ from __future__ import annotations import math -from typing import TYPE_CHECKING, Protocol +from typing import TYPE_CHECKING, Literal, Protocol, TypeVar import attrs @@ -16,13 +16,31 @@ enable_ki_protection, remove_parking_lot_breaker, ) +from ._deprecate import warn_deprecated from ._util import final if TYPE_CHECKING: + from collections.abc import Callable from types import TracebackType + from typing_extensions import deprecated + from ._core import Task from ._core._parking_lot import ParkingLotStatistics +else: + T = TypeVar("T") + + def deprecated( + message: str, + /, + *, + category: type[Warning] | None = DeprecationWarning, + stacklevel: int = 1, + ) -> Callable[[T], T]: + def wrapper(f: T) -> T: + return f + + return wrapper @attrs.frozen @@ -112,6 +130,20 @@ def statistics(self) -> EventStatistics: """ return EventStatistics(tasks_waiting=len(self._tasks)) + @deprecated( + "trio.Event.__bool__ is deprecated since Trio 0.31.0; use trio.Event.is_set instead (https://github.com/python-trio/trio/issues/3238)", + stacklevel=2, + ) + def __bool__(self) -> Literal[True]: + """Return True and raise warning.""" + warn_deprecated( + self.__bool__, + "0.31.0", + issue=3238, + instead=self.is_set, + ) + return True + class _HasAcquireRelease(Protocol): """Only classes with acquire() and release() can use the mixin's implementations.""" diff --git a/src/trio/_tests/test_sync.py b/src/trio/_tests/test_sync.py index 39f8d21f3..6096510d3 100644 --- a/src/trio/_tests/test_sync.py +++ b/src/trio/_tests/test_sync.py @@ -23,6 +23,12 @@ async def test_Event() -> None: assert not e.is_set() assert e.statistics().tasks_waiting == 0 + with pytest.warns( + DeprecationWarning, + match=r"trio\.Event\.__bool__ is deprecated since Trio 0\.31\.0; use trio\.Event\.is_set instead \(https://github.com/python-trio/trio/issues/3238\)", + ): + e.__bool__() + e.set() assert e.is_set() with assert_checkpoints(): diff --git a/test-requirements.txt b/test-requirements.txt index 3d12554ce..c11c47e7a 100644 --- a/test-requirements.txt +++ b/test-requirements.txt @@ -187,7 +187,7 @@ types-pyyaml==6.0.12.20250822 # via -r test-requirements.in types-setuptools==80.9.0.20250822 # via types-cffi -typing-extensions==4.14.1 +typing-extensions==4.15.0 # via # -r test-requirements.in # astroid