## Problem
The AST component index (`buildAstIndexWithDiagnostics`) is keyed by
component **name**. When two files define a component with the same name
— most commonly platform variants, e.g. `List` in `List.tsx` and `List`
in `List.web.tsx` — the index kept whichever file the directory walk
happened to reach **first** (`if (!index.has(name))`) and threw the rest
away.
So a lookup for `List` could return the wrong platform variant's source,
with no signal that other matches even existed. And because it depended
on filesystem walk order, *which* `List` survived was effectively
arbitrary.
Raised in review on #287.
## Fix
- **Collect every match per name** instead of keeping the first walked.
- **Choose a deterministic primary**: base files are preferred over
`.web` / `.ios` / `.android` / `.native` variants (those only override
the base when bundling for that platform), then ties break on path →
line → column. The result no longer depends on directory-walk order.
- **Surface the rest** as `otherMatches` on the index entry.
`react-profiler-component-source` now returns `otherMatches: [{ file,
line, col }]` alongside the primary, so a caller asking for `List` can
tell the locations apart instead of trusting a single arbitrary file.
`react-profiler-analyze` needs no change — it enriches findings with the
(now deterministic) primary location, which is strictly better than
before; surfacing per-finding alternates there is out of scope.
## Tests
`packages/tool-server/test/react-profiler/ast-index.test.ts` (index
layer) and a new `component-source-duplicates.test.ts` (end-to-end
through the tool's `execute`):
- same name in `List.tsx` + `List.web.tsx` → primary is the base file,
its source is returned, `List.web.tsx` is under `otherMatches`;
- only platform variants (`.android` + `.ios`, no base) → deterministic
primary by path;
- uniquely-named component → no `otherMatches`.
The two collision assertions fail on pre-fix code (no `otherMatches`,
arbitrary primary) and pass with the fix. Verified locally with Node 20:
`vitest run test/react-profiler/` — 80 passed; `tsc --build` clean;
prettier + eslint clean.