Zombie Code
Zombie code is alive on paper and dead in practice. The functions call each other, the imports resolve, the compiler is happy β and no entry point in your application ever reaches any of them. Mapnostics finds them by building the call graph and walking it from every real entry point.
Zombie versus dead
The two scans answer different questions, which is why they are separate tabs with separate counts.
- Dead code has no caller at all. A single export that nothing imports.
- Zombie code has callers. It sits inside a cluster of functions that call one another, and the whole cluster is orphaned β nothing outside it ever calls in.
Dead-code scanners miss zombies for exactly this reason: every function in the cluster has a reference, so a reference count never drops to zero. Only reachability from an entry point tells you the truth.
How detection runs
The scan has three phases and runs in batches from your browser, so you can stop it and resume:
- Clear β previous zombie findings for this repository are removed, so a re-run never mixes two scans.
- Build the call graph β every file is walked and each call site recorded as an edge.
- Detect β the graph is walked from every entry point. Whatever is never reached is a zombie.
The tab
The call chain
Every zombie finding can show the chain behind it: Nobody calls A β B β C β all zombie. Read it as the path the scan followed. The first name is the function nothing outside the cluster calls, and each arrow is a call it makes into the rest of the orphaned group.
The chain is what makes a zombie safe to act on. It names the whole cluster to delete rather than one function whose removal would only break the next one along.
Confidence
Zombie findings carry the same confidence scale as dead code, and the same filter: All, High (β₯90%), Medium. Dynamic dispatch is the usual reason a score sits in the middle β a call made through a variable cannot be resolved statically, so the scan cannot rule out a caller it never saw.
Feature flags
A card below the findings scans for feature flags, because a flag that has been hard-off for a year is the most common way live code becomes unreachable. It splits them in two:
- Decided in code β the flag resolves to a constant. Safe to act on from the repository alone.
- Set at runtime β the value comes from a service or an environment variable.
What to do next
- Delete the whole chain, not the head of it. The rest becomes dead code the moment the head goes.
- Check the Impact Simulator for the file first β a zombie cluster can still be imported by a test.
- Look at the feature flags card before concluding a route is unreachable.
- Re-run detection after the deletion merges, so the Health Score reflects it.