From dc5ef20d89f0fc787a97ebd05bb8c41fbce10ab7 Mon Sep 17 00:00:00 2001 From: Teknium <127238744+teknium1@users.noreply.github.com> Date: Mon, 29 Jun 2026 02:42:54 -0700 Subject: [PATCH] test(reasoning-floor): isolate stale-timeout floor tests from config-module reload races (#54775) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The five _resolved_api_call_stale_timeout_base integration tests reloaded hermes_cli.config + hermes_cli.timeouts via importlib.reload to clear cached config. Under xdist that mutates module-global state shared across the worker process, so a sibling test could leave the config cache in a state that made get_provider_stale_timeout return a leaked value — intermittently failing test_reasoning_floor_applies_to_opus_4_thinking (shard 6 flake, #52217 area). Patch run_agent.get_provider_stale_timeout per-test instead: floor-path tests get None (resolver falls through to the reasoning floor / env var / default), the explicit-config test gets 60.0 (priority-1 short-circuit). Same assertions, no shared-module mutation, deterministic under parallel execution. --- .../test_reasoning_stale_timeout_floor.py | 48 ++++++++----------- 1 file changed, 20 insertions(+), 28 deletions(-) diff --git a/tests/agent/test_reasoning_stale_timeout_floor.py b/tests/agent/test_reasoning_stale_timeout_floor.py index 196c34f2dc7..3177b585ab4 100644 --- a/tests/agent/test_reasoning_stale_timeout_floor.py +++ b/tests/agent/test_reasoning_stale_timeout_floor.py @@ -161,11 +161,13 @@ def test_reasoning_floor_applies_to_nemotron_3_ultra(monkeypatch, tmp_path): monkeypatch.delenv("HERMES_API_CALL_STALE_TIMEOUT", raising=False) _write_config(tmp_path, "") - # Clear any cached config from prior tests in this session. - import importlib - from hermes_cli import config as cfg_mod, timeouts as to_mod - importlib.reload(cfg_mod) - importlib.reload(to_mod) + # Isolate the floor path from leaked provider config: with no per-model / + # per-provider stale_timeout_seconds, the resolver falls through to the + # reasoning floor. Patch the lookup to return None deterministically + # rather than relying on importlib.reload of shared config modules, which + # races other tests in the same xdist worker (#52217 flake). + import run_agent + monkeypatch.setattr(run_agent, "get_provider_stale_timeout", lambda *a, **k: None) agent = _make_agent( tmp_path, @@ -190,10 +192,9 @@ def test_reasoning_floor_applies_to_opus_4_thinking(monkeypatch, tmp_path): monkeypatch.delenv("HERMES_API_CALL_STALE_TIMEOUT", raising=False) _write_config(tmp_path, "") - import importlib - from hermes_cli import config as cfg_mod, timeouts as to_mod - importlib.reload(cfg_mod) - importlib.reload(to_mod) + # Deterministic floor path — see test_reasoning_floor_applies_to_nemotron_3_ultra. + import run_agent + monkeypatch.setattr(run_agent, "get_provider_stale_timeout", lambda *a, **k: None) agent = _make_agent( tmp_path, @@ -216,19 +217,12 @@ def test_reasoning_floor_never_overrides_explicit_user_config(monkeypatch, tmp_p """ monkeypatch.setenv("HERMES_HOME", str(tmp_path)) (tmp_path / ".env").write_text("", encoding="utf-8") - _write_config(tmp_path, """\ -providers: - nvidia: - models: - nvidia/nemotron-3-ultra-550b-a55b: - stale_timeout_seconds: 60 -""") monkeypatch.delenv("HERMES_API_CALL_STALE_TIMEOUT", raising=False) - import importlib - from hermes_cli import config as cfg_mod, timeouts as to_mod - importlib.reload(cfg_mod) - importlib.reload(to_mod) + # Explicit per-model config resolves to 60s (priority 1). The resolver + # must short-circuit on this and never consult the reasoning floor. + import run_agent + monkeypatch.setattr(run_agent, "get_provider_stale_timeout", lambda *a, **k: 60.0) agent = _make_agent( tmp_path, @@ -251,10 +245,9 @@ def test_reasoning_floor_loses_to_env_var_when_no_floor_match(monkeypatch, tmp_p monkeypatch.setenv("HERMES_API_CALL_STALE_TIMEOUT", "300") _write_config(tmp_path, "") - import importlib - from hermes_cli import config as cfg_mod, timeouts as to_mod - importlib.reload(cfg_mod) - importlib.reload(to_mod) + # No provider config -> resolver consults the env var (priority 3). + import run_agent + monkeypatch.setattr(run_agent, "get_provider_stale_timeout", lambda *a, **k: None) agent = _make_agent( tmp_path, @@ -274,10 +267,9 @@ def test_non_reasoning_model_keeps_default(monkeypatch, tmp_path): monkeypatch.delenv("HERMES_API_CALL_STALE_TIMEOUT", raising=False) _write_config(tmp_path, "") - import importlib - from hermes_cli import config as cfg_mod, timeouts as to_mod - importlib.reload(cfg_mod) - importlib.reload(to_mod) + # No provider config, no env var, no floor match -> 90s implicit default. + import run_agent + monkeypatch.setattr(run_agent, "get_provider_stale_timeout", lambda *a, **k: None) agent = _make_agent( tmp_path,