diff --git a/backend/apps/agents/core/fault_injection.py b/backend/apps/agents/core/fault_injection.py index ac060fdd..11f4fe26 100644 --- a/backend/apps/agents/core/fault_injection.py +++ b/backend/apps/agents/core/fault_injection.py @@ -28,6 +28,7 @@ KNOWN_FAULTS: Set[str] = { "dead_lane", # the router has already given up on the credential (ENG-414 preflight) "cli_context_squeeze", # a tiny context window, so autocompact thrash is drillable (ENG-418) "stale_tool_schema", # the CLI's deferred-tool 400, byte-real incl. truncation (ENG-394 wall 2) + "unclassified_error", # a raw runtime failure no classifier owns, so the snag card is drillable (self-heal audit) } # The window `cli_context_squeeze` pretends the model has, and the number is load-bearing. diff --git a/backend/apps/agents/manager/run/TurnRunner.py b/backend/apps/agents/manager/run/TurnRunner.py index 2d146182..c186656f 100644 --- a/backend/apps/agents/manager/run/TurnRunner.py +++ b/backend/apps/agents/manager/run/TurnRunner.py @@ -75,6 +75,10 @@ class TurnRunner(AgentManagerProtocol): "'mcp__openswarm-core__ShowUI' cannot have both defer_loading=true and cache_ " "(reset after 15s)\"}}" ) + # One-shot, and deliberately a text NO classifier owns: it must fall through to the generic + # branch, whose raw "Error: ..." card used to render as nothing at all (self-heal audit, 2026-09-01). + if p_fault_once("unclassified_error"): + raise RuntimeError("Command failed with exit code 1 (exit code: 1)\nError output: Check stderr output for details") async def prompt_stream(): yield { diff --git a/backend/tests/test_fault_injection.py b/backend/tests/test_fault_injection.py index c5caebf0..4e275177 100644 --- a/backend/tests/test_fault_injection.py +++ b/backend/tests/test_fault_injection.py @@ -63,6 +63,7 @@ WIRED_IN = { "dead_lane": "backend/apps/agents/manager/run/lane_preflight.py", "cli_context_squeeze": "backend/apps/agents/manager/configure_provider_env.py", "stale_tool_schema": TURN_RUNNER, + "unclassified_error": TURN_RUNNER, } @@ -181,3 +182,19 @@ def test_the_harness_declares_what_it_cannot_reach(): from backend.apps.agents.core.fault_injection import UNREACHABLE_WITH assert "empty_finish" in UNREACHABLE_WITH assert set(UNREACHABLE_WITH) <= KNOWN_FAULTS + + +def test_the_unclassified_fault_is_owned_by_no_classifier(): + """The drill exists to reach the generic branch; if any classifier ever claims this text the + drill silently measures a different door.""" + from backend.apps.agents.core.error_classify import ( + is_auth_error, is_connection_lost, is_context_overflow_error, is_external_kill_error, + is_stale_tool_schema_error, is_transient_capacity_error, + ) + text = re.search(r'RuntimeError\("(.+?)"\)', p_block("unclassified_error")).group(1).encode().decode("unicode_escape") + exc = RuntimeError(text) + assert "exit code 1 " in text or "exit code 1\n" in text + for pred in (is_external_kill_error, is_stale_tool_schema_error, is_transient_capacity_error, is_context_overflow_error): + assert not pred(exc), pred.__name__ + assert not is_auth_error(exc) + assert not is_connection_lost(exc)