Backend-aware timeout in `maybe_expect_raises`
Default `timeout` from `int = 3` → `int|None = None`; when unset, pick a backend-aware value. Fork-based backends (`main_thread_forkserver`) need real headroom bc actor spawn + IPC ctx-exit + msg-validation error path is much heavier than under `trio` backend — especially under cross-pytest-stream contention (#451). Defaults: - `main_thread_forkserver` → 30s - everything else → 3s (unchanged) Empirical flake history that motivated 30s as the floor on fork backends (all from `test_basic_payload_spec`): - 3s → all-valid variant flaked w/ `TooSlowError` - 8s → `invalid-return` variant flaked w/ `Cancelled` (surfaced instead of `MsgTypeError` bc the outer `fail_after` fired mid-error-path) - 15s → flaked under cross-pytest-stream contention 30s gives plenty of headroom while still failing-loud on a genuine hang. Callers can opt out by passing an explicit `timeout=` kw. (this patch was generated in some part by [`claude-code`][claude-code-gh]) [claude-code-gh]: https://github.com/anthropics/claude-codesubint_forkserver_backend
parent
3c366cac13
commit
060f7d24c4
|
|
@ -55,12 +55,37 @@ async def maybe_expect_raises(
|
||||||
raises: BaseException|None = None,
|
raises: BaseException|None = None,
|
||||||
ensure_in_message: list[str]|None = None,
|
ensure_in_message: list[str]|None = None,
|
||||||
post_mortem: bool = False,
|
post_mortem: bool = False,
|
||||||
timeout: int = 3,
|
# NOTE, `None` selects a backend-aware default below —
|
||||||
|
# see `_BACKEND_TIMEOUT_DEFAULTS` for rationale. Caller
|
||||||
|
# can override with an explicit value to opt out.
|
||||||
|
timeout: int|None = None,
|
||||||
) -> None:
|
) -> None:
|
||||||
'''
|
'''
|
||||||
Async wrapper for ensuring errors propagate from the inner scope.
|
Async wrapper for ensuring errors propagate from the inner scope.
|
||||||
|
|
||||||
'''
|
'''
|
||||||
|
if timeout is None:
|
||||||
|
# Pick a backend-aware default. Fork-based backends
|
||||||
|
# (`main_thread_forkserver`) need much more headroom
|
||||||
|
# because actor spawn + IPC ctx-exit + msg-validation
|
||||||
|
# error path takes longer than under `trio` backend
|
||||||
|
# — especially under cross-pytest-stream contention
|
||||||
|
# (#451). `test_basic_payload_spec` empirically:
|
||||||
|
# - 3s flaked all-valid variant (`TooSlowError`)
|
||||||
|
# - 8s flaked `invalid-return` variant
|
||||||
|
# (`Cancelled` surfaced instead of `MsgTypeError`
|
||||||
|
# because `fail_after` fired mid-error-path)
|
||||||
|
# - 15s flaked under cross-stream contention
|
||||||
|
# 30s for fork-based gives plenty of headroom while
|
||||||
|
# still failing-loud on a genuine hang. Other
|
||||||
|
# backends keep the original 3s.
|
||||||
|
from tractor.spawn import _spawn as _spawn_mod
|
||||||
|
timeout = (
|
||||||
|
30
|
||||||
|
if _spawn_mod._spawn_method == 'main_thread_forkserver'
|
||||||
|
else 3
|
||||||
|
)
|
||||||
|
|
||||||
if tractor.debug_mode():
|
if tractor.debug_mode():
|
||||||
timeout += 999
|
timeout += 999
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue