Source: python-trio Version: 0.25.0-1 Severity: normal User: [email protected] Usertags: python3.13 Forwarded: https://github.com/python-trio/trio/issues/3004
This package failed build from source when test-built against a version of python3-defaults that includes 3.13 as a supported version. To reproduce this issue, build against python3-defaults (python3-all-dev etc.) from Debian experimental. What's new in Python 3.13: https://docs.python.org/3.13/whatsnew/3.13.html Log snippet: dh_auto_test -O--buildsystem=pybuild I: pybuild base:311: cd /<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build; python3.13 -m pytest -m "not redistributors_should_skip" -p trio._tests.pytest_plugin -k "not test_SocketType_resolve and not test_getprotobyname" --skip-optional-imports ============================= test session starts ============================== platform linux -- Python 3.13.0rc2, pytest-8.3.3, pluggy-1.5.0 rootdir: /<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build configfile: pyproject.toml plugins: typeguard-4.3.0 collected 776 items / 45 deselected / 1 skipped / 731 selected trio/_core/_tests/test_asyncgen.py ....... [ 0%] trio/_core/_tests/test_exceptiongroup_gc.py .. [ 1%] trio/_core/_tests/test_guest_mode.py .............. [ 3%] trio/_core/_tests/test_instrumentation.py ........ [ 4%] trio/_core/_tests/test_io.py ............................ [ 8%] trio/_core/_tests/test_ki.py .F.....F... [ 9%] trio/_core/_tests/test_local.py .... [ 10%] trio/_core/_tests/test_mock_clock.py .....s [ 10%] trio/_core/_tests/test_parking_lot.py .... [ 11%] trio/_core/_tests/test_run.py ................................s......... [ 17%] ........................................................................ [ 27%] ................................. [ 31%] trio/_core/_tests/test_thread_cache.py ..ss.. [ 32%] trio/_core/_tests/test_tutil.py . [ 32%] trio/_core/_tests/test_unbounded_queue.py ..... [ 33%] trio/_core/_tests/test_windows.py sssssss [ 34%] trio/_tests/test_abc.py ... [ 34%] trio/_tests/test_channel.py ............. [ 36%] trio/_tests/test_contextvars.py ... [ 36%] trio/_tests/test_deprecate.py ........... [ 38%] trio/_tests/test_deprecate_strict_exception_groups_false.py ... [ 38%] trio/_tests/test_dtls.py ..s.............s............. [ 42%] trio/_tests/test_exports.py ... [ 43%] trio/_tests/test_fakenet.py ....s.... [ 44%] trio/_tests/test_file_io.py ................. [ 46%] trio/_tests/test_highlevel_generic.py .. [ 47%] trio/_tests/test_highlevel_open_tcp_listeners.py .................... [ 49%] trio/_tests/test_highlevel_open_tcp_stream.py ....................... [ 52%] trio/_tests/test_highlevel_open_unix_stream.py .....s [ 53%] trio/_tests/test_highlevel_serve_listeners.py .... [ 54%] trio/_tests/test_highlevel_socket.py ....... [ 55%] trio/_tests/test_highlevel_ssl_helpers.py ... [ 55%] trio/_tests/test_path.py .s................F................ [ 60%] trio/_tests/test_scheduler_determinism.py .. [ 60%] trio/_tests/test_signals.py ........ [ 61%] trio/_tests/test_socket.py .......s....................... [ 66%] trio/_tests/test_ssl.py ......s.............................s........... [ 72%] ............... [ 74%] trio/_tests/test_subprocess.py ....................s........ [ 78%] trio/_tests/test_sync.py .................................. [ 83%] trio/_tests/test_testing.py ................... [ 85%] trio/_tests/test_testing_raisesgroup.py .......... [ 87%] trio/_tests/test_threads.py F.F......................................... [ 93%] .s.... [ 94%] trio/_tests/test_timeouts.py sss. [ 94%] trio/_tests/test_tracing.py .. [ 94%] trio/_tests/test_unix_pipes.py ........... [ 96%] trio/_tests/test_util.py ......... [ 97%] trio/_tests/test_wait_for_object.py ssss [ 98%] trio/_tests/test_windows_pipes.py ssssss [ 99%] trio/_tests/tools/test_mypy_annotate.py ....... [100%] =================================== FAILURES =================================== _______________________________ test_ki_enabled ________________________________ async def test_ki_enabled() -> None: # Regular tasks aren't KI-protected assert not _core.currently_ki_protected() # Low-level call-soon callbacks are KI-protected token = _core.current_trio_token() record = [] def check() -> None: record.append(_core.currently_ki_protected()) token.run_sync_soon(check) await wait_all_tasks_blocked() assert record == [True] @_core.enable_ki_protection def protected() -> None: assert _core.currently_ki_protected() unprotected() @_core.disable_ki_protection def unprotected() -> None: assert not _core.currently_ki_protected() > protected() trio/_core/_tests/test_ki.py:62: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ trio/_core/_ki.py:181: in wrapper return fn(*args, **kwargs) _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ @_core.enable_ki_protection def protected() -> None: > assert _core.currently_ki_protected() E assert False E + where False = <function currently_ki_protected at 0xffff83496700>() E + where <function currently_ki_protected at 0xffff83496700> = _core.currently_ki_protected trio/_core/_tests/test_ki.py:55: AssertionError ___________________________ test_ki_disabled_in_del ____________________________ def test_ki_disabled_in_del() -> None: def nestedfunction() -> bool: return _core.currently_ki_protected() def __del__() -> None: assert _core.currently_ki_protected() assert nestedfunction() @_core.disable_ki_protection def outerfunction() -> None: assert not _core.currently_ki_protected() assert not nestedfunction() __del__() __del__() > outerfunction() trio/_core/_tests/test_ki.py:255: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ trio/_core/_ki.py:181: in wrapper return fn(*args, **kwargs) _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ @_core.disable_ki_protection def outerfunction() -> None: > assert not _core.currently_ki_protected() E assert not True E + where True = <function currently_ki_protected at 0xffff83496700>() E + where <function currently_ki_protected at 0xffff83496700> = _core.currently_ki_protected trio/_core/_tests/test_ki.py:250: AssertionError _________________________ test_async_method_signature __________________________ path = trio.Path('/tmp/pytest-of-debusine-worker/pytest-0/test_async_method_signature0/test') async def test_async_method_signature(path: trio.Path) -> None: # use `resolve` as a representative of wrapped methods assert path.resolve.__name__ == "resolve" assert path.resolve.__qualname__ == "Path.resolve" assert path.resolve.__doc__ is not None > assert "pathlib.Path.resolve" in path.resolve.__doc__ E AssertionError: assert 'pathlib.Path.resolve' in 'Like :meth:`~pathlib._local.Path.resolve`, but async.\n\nMake the path absolute, resolving all symlinks on the way and also\nnormalizing it.\n' E + where 'Like :meth:`~pathlib._local.Path.resolve`, but async.\n\nMake the path absolute, resolving all symlinks on the way and also\nnormalizing it.\n' = resolve.__doc__ E + where resolve = trio.Path('/tmp/pytest-of-debusine-worker/pytest-0/test_async_method_signature0/test').resolve trio/_tests/test_path.py:125: AssertionError ____________________________ test_do_in_trio_thread ____________________________ async def test_do_in_trio_thread() -> None: trio_thread = threading.current_thread() async def check_case( do_in_trio_thread: Callable[..., threading.Thread], fn: Callable[..., T | Awaitable[T]], expected: tuple[str, T], trio_token: _core.TrioToken | None = None, ) -> None: record: RecordType = [] def threadfn() -> None: try: record.append(("start", threading.current_thread())) x = do_in_trio_thread(fn, record, trio_token=trio_token) record.append(("got", x)) except BaseException as exc: print(exc) record.append(("error", type(exc))) child_thread = threading.Thread(target=threadfn, daemon=True) child_thread.start() while child_thread.is_alive(): print("yawn") await sleep(0.01) assert record == [("start", child_thread), ("f", trio_thread), expected] token = _core.current_trio_token() def f1(record: RecordType) -> int: assert not _core.currently_ki_protected() record.append(("f", threading.current_thread())) return 2 > await check_case(from_thread_run_sync, f1, ("got", 2), trio_token=token) trio/_tests/test_threads.py:94: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ do_in_trio_thread = <function run_sync at 0xffff8314d620> fn = <function test_do_in_trio_thread.<locals>.f1 at 0xffff82018220> expected = ('got', 2) trio_token = TrioToken(_reentry_queue=EntryQueue(queue=deque([]), idempotent_queue={}, wakeup=<trio._core._wakeup_socketpair.WakeupSocketpair object at 0xffff8213ed50>, done=True, lock=<unlocked _thread.RLock object owner=0 count=0 at 0xffff82517740>)) async def check_case( do_in_trio_thread: Callable[..., threading.Thread], fn: Callable[..., T | Awaitable[T]], expected: tuple[str, T], trio_token: _core.TrioToken | None = None, ) -> None: record: RecordType = [] def threadfn() -> None: try: record.append(("start", threading.current_thread())) x = do_in_trio_thread(fn, record, trio_token=trio_token) record.append(("got", x)) except BaseException as exc: print(exc) record.append(("error", type(exc))) child_thread = threading.Thread(target=threadfn, daemon=True) child_thread.start() while child_thread.is_alive(): print("yawn") await sleep(0.01) > assert record == [("start", child_thread), ("f", trio_thread), expected] E AssertionError: assert [('start', <T...rtionError'>)] == [('start', <T...), ('got', 2)] E E At index 1 diff: ('error', <class 'AssertionError'>) != ('f', <_MainThread(MainThread, started 281472901461824)>) E Right contains one more item: ('got', 2) E Use -v to get more diff trio/_tests/test_threads.py:85: AssertionError ----------------------------- Captured stdout call ----------------------------- yawn assert not True + where True = <function currently_ki_protected at 0xffff83496700>() + where <function currently_ki_protected at 0xffff83496700> = _core.currently_ki_protected __________________________ test_run_in_trio_thread_ki __________________________ def test_run_in_trio_thread_ki() -> None: # if we get a control-C during a run_in_trio_thread, then it propagates # back to the caller (slick!) record = set() async def check_run_in_trio_thread() -> None: token = _core.current_trio_token() def trio_thread_fn() -> None: print("in Trio thread") assert not _core.currently_ki_protected() print("ki_self") try: ki_self() finally: import sys print("finally", sys.exc_info()) async def trio_thread_afn() -> None: trio_thread_fn() def external_thread_fn() -> None: try: print("running") from_thread_run_sync(trio_thread_fn, trio_token=token) except KeyboardInterrupt: print("ok1") record.add("ok1") try: from_thread_run(trio_thread_afn, trio_token=token) except KeyboardInterrupt: print("ok2") record.add("ok2") thread = threading.Thread(target=external_thread_fn) thread.start() print("waiting") while thread.is_alive(): await sleep(0.01) print("waited, joining") thread.join() print("done") _core.run(check_run_in_trio_thread) > assert record == {"ok1", "ok2"} E AssertionError: assert set() == {'ok1', 'ok2'} E E Extra items in the right set: E 'ok2' E 'ok1' E Use -v to get more diff trio/_tests/test_threads.py:176: AssertionError During handling of the above exception, another exception occurred: cls = <class '_pytest.runner.CallInfo'> func = <function call_and_report.<locals>.<lambda> at 0xffff81f854e0> when = 'call' reraise = (<class '_pytest.outcomes.Exit'>, <class 'KeyboardInterrupt'>) @classmethod def from_call( cls, func: Callable[[], TResult], when: Literal["collect", "setup", "call", "teardown"], reraise: type[BaseException] | tuple[type[BaseException], ...] | None = None, ) -> CallInfo[TResult]: """Call func, wrapping the result in a CallInfo. :param func: The function to call. Called without arguments. :type func: Callable[[], _pytest.runner.TResult] :param when: The phase in which the function is called. :param reraise: Exception or exceptions that shall propagate if raised by the function, instead of being wrapped in the CallInfo. """ excinfo = None start = timing.time() precise_start = timing.perf_counter() try: > result: TResult | None = func() /usr/lib/python3/dist-packages/_pytest/runner.py:341: _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ /usr/lib/python3/dist-packages/_pytest/runner.py:242: in <lambda> lambda: runtest_hook(item=item, **kwds), when=when, reraise=reraise /usr/lib/python3/dist-packages/pluggy/_hooks.py:513: in __call__ return self._hookexec(self.name, self._hookimpls.copy(), kwargs, firstresult) /usr/lib/python3/dist-packages/pluggy/_manager.py:120: in _hookexec return self._inner_hookexec(hook_name, methods, kwargs, firstresult) /usr/lib/python3/dist-packages/_pytest/threadexception.py:92: in pytest_runtest_call yield from thread_exception_runtest_hook() _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ def thread_exception_runtest_hook() -> Generator[None]: with catch_threading_exception() as cm: try: yield finally: if cm.args: thread_name = ( "<unknown>" if cm.args.thread is None else cm.args.thread.name ) msg = f"Exception in thread {thread_name}\n\n" msg += "".join( traceback.format_exception( cm.args.exc_type, cm.args.exc_value, cm.args.exc_traceback, ) ) > > warnings.warn(pytest.PytestUnhandledThreadExceptionWarning(msg)) E pytest.PytestUnhandledThreadExceptionWarning: Exception in thread Thread-5 (external_thread_fn) E E Traceback (most recent call last): E File "/usr/lib/python3.13/threading.py", line 1041, in _bootstrap_inner E self.run() E ~~~~~~~~^^ E File "/usr/lib/python3.13/threading.py", line 992, in run E self._target(*self._args, **self._kwargs) E ~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ E File "/<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build/trio/_tests/test_threads.py", line 156, in external_thread_fn E from_thread_run_sync(trio_thread_fn, trio_token=token) E ~~~~~~~~~~~~~~~~~~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ E File "/<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build/trio/_threads.py", line 630, in from_thread_run_sync E return _send_message_to_trio(trio_token, RunSync(fn, args)) E File "/<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build/trio/_threads.py", line 549, in _send_message_to_trio E return message_to_trio.queue.get().unwrap() E ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~^^ E File "/usr/lib/python3/dist-packages/outcome/_impl.py", line 138, in unwrap E raise captured_error E File "/<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build/trio/_core/_ki.py", line 181, in wrapper E return fn(*args, **kwargs) E File "/<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build/trio/_threads.py", line 217, in unprotected_fn E ret = self.context.run(self.fn, *self.args) E File "/<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build/trio/_tests/test_threads.py", line 141, in trio_thread_fn E assert not _core.currently_ki_protected() E AssertionError: assert not True E + where True = <function currently_ki_protected at 0xffff83496700>() E + where <function currently_ki_protected at 0xffff83496700> = _core.currently_ki_protected /usr/lib/python3/dist-packages/_pytest/threadexception.py:82: PytestUnhandledThreadExceptionWarning ----------------------------- Captured stdout call ----------------------------- running waiting in Trio thread waited, joining done =========================== short test summary info ============================ FAILED trio/_core/_tests/test_ki.py::test_ki_enabled - assert False FAILED trio/_core/_tests/test_ki.py::test_ki_disabled_in_del - assert not True FAILED trio/_tests/test_path.py::test_async_method_signature - AssertionError... FAILED trio/_tests/test_threads.py::test_do_in_trio_thread - AssertionError: ... FAILED trio/_tests/test_threads.py::test_run_in_trio_thread_ki - pytest.Pytes... ========== 5 failed, 692 passed, 35 skipped, 45 deselected in 10.43s =========== E: pybuild pybuild:389: test: plugin pyproject failed with: exit code=1: cd /<<PKGBUILDDIR>>/.pybuild/cpython3_3.13_trio/build; python3.13 -m pytest -m "not redistributors_should_skip" -p trio._tests.pytest_plugin -k "not test_SocketType_resolve and not test_getprotobyname" --skip-optional-imports I: pybuild base:311: cd /<<PKGBUILDDIR>>/.pybuild/cpython3_3.12_trio/build; python3.12 -m pytest -m "not redistributors_should_skip" -p trio._tests.pytest_plugin -k "not test_SocketType_resolve and not test_getprotobyname" --skip-optional-imports ============================= test session starts ============================== platform linux -- Python 3.12.6, pytest-8.3.3, pluggy-1.5.0 rootdir: /<<PKGBUILDDIR>>/.pybuild/cpython3_3.12_trio/build configfile: pyproject.toml plugins: typeguard-4.3.0 collected 776 items / 45 deselected / 1 skipped / 731 selected trio/_core/_tests/test_asyncgen.py ....... [ 0%] trio/_core/_tests/test_exceptiongroup_gc.py .. [ 1%] trio/_core/_tests/test_guest_mode.py .............. [ 3%] trio/_core/_tests/test_instrumentation.py ........ [ 4%] trio/_core/_tests/test_io.py ............................ [ 8%] trio/_core/_tests/test_ki.py ........... [ 9%] trio/_core/_tests/test_local.py .... [ 10%] trio/_core/_tests/test_mock_clock.py .....s [ 10%] trio/_core/_tests/test_parking_lot.py .... [ 11%] trio/_core/_tests/test_run.py ................................s......... [ 17%] ........................................................................ [ 27%] ................................. [ 31%] trio/_core/_tests/test_thread_cache.py ..ss.. [ 32%] trio/_core/_tests/test_tutil.py . [ 32%] trio/_core/_tests/test_unbounded_queue.py ..... [ 33%] trio/_core/_tests/test_windows.py sssssss [ 34%] trio/_tests/test_abc.py ... [ 34%] trio/_tests/test_channel.py ............. [ 36%] trio/_tests/test_contextvars.py ... [ 36%] trio/_tests/test_deprecate.py ........... [ 38%] trio/_tests/test_deprecate_strict_exception_groups_false.py ... [ 38%] trio/_tests/test_dtls.py ..s.............s............. [ 42%] trio/_tests/test_exports.py ... [ 43%] trio/_tests/test_fakenet.py ....s.... [ 44%] trio/_tests/test_file_io.py ................. [ 46%] trio/_tests/test_highlevel_generic.py .. [ 47%] trio/_tests/test_highlevel_open_tcp_listeners.py .................... [ 49%] trio/_tests/test_highlevel_open_tcp_stream.py ....................... [ 52%] trio/_tests/test_highlevel_open_unix_stream.py .....s [ 53%] trio/_tests/test_highlevel_serve_listeners.py .... [ 54%] trio/_tests/test_highlevel_socket.py ....... [ 55%] trio/_tests/test_highlevel_ssl_helpers.py ... [ 55%] trio/_tests/test_path.py .s................................. [ 60%] trio/_tests/test_scheduler_determinism.py .. [ 60%] trio/_tests/test_signals.py ........ [ 61%] trio/_tests/test_socket.py .......s....................... [ 66%] trio/_tests/test_ssl.py ......s.............................s........... [ 72%] ............... [ 74%] trio/_tests/test_subprocess.py ....................s........ [ 78%] trio/_tests/test_sync.py .................................. [ 83%] trio/_tests/test_testing.py ................... [ 85%] trio/_tests/test_testing_raisesgroup.py .......... [ 87%] trio/_tests/test_threads.py ............................................ [ 93%] .s.... [ 94%] trio/_tests/test_timeouts.py sss. [ 94%] trio/_tests/test_tracing.py .. [ 94%] trio/_tests/test_unix_pipes.py ........... [ 96%] trio/_tests/test_util.py ......... [ 97%] trio/_tests/test_wait_for_object.py ssss [ 98%] trio/_tests/test_windows_pipes.py ssssss [ 99%] trio/_tests/tools/test_mypy_annotate.py ....... [100%] ================ 697 passed, 35 skipped, 45 deselected in 9.04s ================ dh_auto_test: error: pybuild --test --test-pytest -i python{version} -p "3.13 3.12" returned exit code 13 make: *** [debian/rules:7: binary] Error 25 dpkg-buildpackage: error: debian/rules binary subprocess returned exit status 2 -------------------------------------------------------------------------------- Build finished at 2024-09-19T09:05:19Z If required, the full build log is available here (for the next 30 days): https://debusine.debian.net/artifact/789934/ This bug has been filed at "normal" severity, as we haven't started the transition to add 3.13 as a supported version, yet. This will be raised to RC as soon as that happens, hopefully well before trixie. Thanks, Stefano

