You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Environment: v0.10.2, Windows 11, daemon mode. Reproduced on a 2-file synthetic repo and on a real Python+TypeScript monorepo (~41.8k nodes / ~198.8k edges, --mode full).
Symptom
A Python from unittest.mock import patch binds to a TypeScript function named patch, in a different language, in a different top-level package. Every with patch(...) in the repo is then recorded as a CALLS edge into that TSX function.
In my real repo this produced a 4-line React helper with 498 inbound callers, all of them backend Python tests:
strategy=unique_name, candidates=1. The resolver is not choosing badly among several candidates — it sees exactly one node named patch in the whole graph and treats that as proof, with no language check and no check that the import specifier (unittest.mock) is external.
This means #1555's proposed fix does not cover this case. That issue asks for better disambiguation when candidates > 1; here candidates == 1, so the ambiguity path is never entered. The two issues are complementary: #1555 is same-language ambiguity, this is a cross-language false positive on a unique name.
Why this is worse than a bad trace hop
The wrong edges silently contaminate the aggregate analyses that agents treat as ground truth:
get_architecture hotspots. The 4-line React helper is reported as the FastAPI empty-path routes not captured #8 hotspot in the repo (fan_in 498), ahead of real infrastructure. Hotspots do not surface confidence, so nothing signals that the entry is fabricated.
Louvain clustering. The node becomes an artificial hub: ~498 backend test functions get pulled into one cluster together with frontend and frontend-mockups, reported at cohesion 0.78. The cluster looks like a genuine architectural seam spanning four packages. It is an artifact.
Dead-code / impact analysis. Anything keying off fan-in inherits the error.
A second instance in the same repo: RuntimeFlagResolver.get reports fan_in 611, whose "callers" are module-level __file__ statements — though that one is at least honestly scored (confidence 0.06, vs 0.95 for the patch edges in the real repo).
Python is especially exposed because stdlib names (patch, get, run, main, setup) collide constantly with short method names in other languages. builtins.* names appear to be handled by a synthetic-node path already; unittest.mock.patch is not a builtin and falls through it.
Suggested fixes
In rough order of value:
Never resolve an import or call across a language boundary. A Python import should not bind to a .tsx node under any strategy. This alone eliminates the whole class.
Treat a resolved import specifier as external when it does not correspond to a project-local module.unittest.mock is not a path in the repo; the specifier is already parsed, since the IMPORTS edge carries local_name. Binding to a synthetic external node (as builtins.* seems to do) would be consistent with existing behavior.
Do not let strategy=unique_name imply high confidence. Uniqueness within the graph is not evidence of a call relationship when the only candidate is in another language/package. Consider capping confidence for cross-package unique_name hits.
Propagate confidence into aggregates.get_architecture hotspots/clusters could exclude or flag edges below a confidence threshold, or expose the weakest strategy contributing to a hotspot. Related: trace_path format=json drops include_evidence strategy and confidence #1542 (strategy/confidence dropped in format=json).
Happy to test a patch against the real repo — the misresolution is deterministic there and easy to re-measure via trace_path --include-evidence.
Environment: v0.10.2, Windows 11, daemon mode. Reproduced on a 2-file synthetic repo and on a real Python+TypeScript monorepo (~41.8k nodes / ~198.8k edges,
--mode full).Symptom
A Python
from unittest.mock import patchbinds to a TypeScript function namedpatch, in a different language, in a different top-level package. Everywith patch(...)in the repo is then recorded as aCALLSedge into that TSX function.In my real repo this produced a 4-line React helper with 498 inbound callers, all of them backend Python tests:
Minimal reproducer
Two files, no dependencies (24 nodes / 28 edges):
frontend/Panel.tsxbackend/test_thing.pyResult:
Root cause: the IMPORTS edge is already wrong, and it is not an ambiguity failure
The bad binding happens at the import, not at the call site:
from unittest.mock import patchresolved to a project-local TSX node. TheCALLSedges then faithfully follow that import binding.The edge metadata is the important part:
strategy=unique_name,candidates=1. The resolver is not choosing badly among several candidates — it sees exactly one node namedpatchin the whole graph and treats that as proof, with no language check and no check that the import specifier (unittest.mock) is external.This means #1555's proposed fix does not cover this case. That issue asks for better disambiguation when
candidates > 1; herecandidates == 1, so the ambiguity path is never entered. The two issues are complementary: #1555 is same-language ambiguity, this is a cross-language false positive on a unique name.Why this is worse than a bad trace hop
The wrong edges silently contaminate the aggregate analyses that agents treat as ground truth:
get_architecturehotspots. The 4-line React helper is reported as the FastAPI empty-path routes not captured #8 hotspot in the repo (fan_in 498), ahead of real infrastructure. Hotspots do not surfaceconfidence, so nothing signals that the entry is fabricated.frontendandfrontend-mockups, reported at cohesion 0.78. The cluster looks like a genuine architectural seam spanning four packages. It is an artifact.A second instance in the same repo:
RuntimeFlagResolver.getreportsfan_in 611, whose "callers" are module-level__file__statements — though that one is at least honestly scored (confidence 0.06, vs 0.95 for thepatchedges in the real repo).Python is especially exposed because stdlib names (
patch,get,run,main,setup) collide constantly with short method names in other languages.builtins.*names appear to be handled by a synthetic-node path already;unittest.mock.patchis not a builtin and falls through it.Suggested fixes
In rough order of value:
importshould not bind to a.tsxnode under any strategy. This alone eliminates the whole class.unittest.mockis not a path in the repo; the specifier is already parsed, since theIMPORTSedge carrieslocal_name. Binding to a synthetic external node (asbuiltins.*seems to do) would be consistent with existing behavior.strategy=unique_nameimply high confidence. Uniqueness within the graph is not evidence of a call relationship when the only candidate is in another language/package. Consider capping confidence for cross-packageunique_namehits.get_architecturehotspots/clusters could exclude or flag edges below a confidence threshold, or expose the weakest strategy contributing to a hotspot. Related: trace_path format=json drops include_evidence strategy and confidence #1542 (strategy/confidence dropped informat=json).Happy to test a patch against the real repo — the misresolution is deterministic there and easy to re-measure via
trace_path --include-evidence.