AGENTS.md
+25 −2
https://raw.githubusercontent.com/hslee16/archy/HEAD/AGENTS.md
− `src/archy/cli.py`, and its tool's return model in `src/archy/mcp.py`. A fourth− the restore and make a clean tree report the mutated behaviour.+ uv run archy contracts . # transitive forbid rules, derived from archy.yaml+ `src/archy/cli_render.py` (the command wiring stays in `src/archy/cli.py`), and its tool's return model in `src/archy/mcp_payloads.py` (the tool wiring stays in `src/archy/mcp.py` and the work behind each tool in `src/archy/mcp_runs.py`). A fourth+ **A name that matched nothing is a refusal, not an empty result.** `archy_dsm`+ with a mistyped `focus` returned `back_edge_count=0`, which a clean project also+ reports, and `simulate` printed `overall +0.000` for an edge it never applied+ (#625, #627). Raise, or put the unresolved state in the verdict itself+ (`coverage`, `nothing_resolved`), and name the near misses with+ `graph.suggest_modules`. It suggests and never accepts: resolving a bare `cli`+ to one of `archy.cli` and every `tests.*cli*` module would be a guess. Search for+ an existing ticket by the symptom ("empty", "exits 0"), not only the mechanism:+ #556 already described the dsm case and a mechanism-worded search missed it.+ **mcp 2.x used to drop a tool's `ValueError` text** (#636, fixed). Expected+ refusals (`ValueError` / `LookupError`) are re-raised as `ToolError` at the tool+ boundary so the reason reaches agents on both majors. Pin the exact message on+ the direct `mcp_runs.run_*` call and through `_call_tool`. Reproduce the+ `mcp 2.x compatibility` job locally with its own install (`uv venv`, then+ `uv pip install -e ".[contracts]" "mcp>=2,<3" pytest pytest-snapshot`) before+ pushing a change to a tool's error path.+ the restore and make a clean tree report the mutated behaviour. A third: **a+ mutation that did not apply is inert too.** A helper whose replacement string+ fails to match leaves the tree unmutated and the suite "survives"; make the+ helper exit non-zero when the match is missing, and read its "applied" line. That+ happened once in #633. In the same PR one test could never fail, though its+ mutation applied, because it named `os.path` as an external node when external+ nodes are top-level names (`os`, `requests`).