Ghost-scan: turn an existing repo into a tracked feature graph
Jun 3, 2026 · 3 min read · ghost-scan, brownfield, adoption, journeys
Most lifecycle tools assume a greenfield start: define the product, then build into it. Real codebases don’t work that way. The features already exist — they’re just scattered across source files, half-documented, untracked.
Ghost-scan meets that reality. Point it at an existing repository and it produces feature candidates — each with a confidence score and the source, test, and doc files it detected as evidence.
One pass never finds everything
A single heuristic walk is only a seed. It misses features that span modules, hide behind entry points, or are only legible from tests, data models, or docs. So the scan fans out: a batch of parallel, read-only analysis lenses — adaptive in number, capped at twelve — each read the repo from a different angle, then consolidate in one place. You get the recall of many perspectives, and none of them ever touch your code.
Tests and docs are first-class scan data, not an afterthought. Each candidate globs its co-located tests and docs — an empty list means “looked and found none,” never “skipped.” That evidence is what makes everything downstream real.
> /zensu:ghost-scan product: acme-api
Phase 1 0 tracked features · 0 journeys loaded
Phase 2 seed walk — 214 files, 9 modules
Phase 2b fan-out — 6 read-only lenses (entrypoints · data-model ·
tests · docs · security · journeys)
candidate conf src test docs
authentication 0.86 7 4 2
billing 0.78 5 3 1
webhook-delivery 0.61 4 2 0 ← globbed, none found
> approve all → ghost_apply (enrich_existing=true)
applied 3 features · linked 16 src, 9 test, 3 doc files
journeys "sign up → first API call" · health 72%
Review, don’t rubber-stamp
Candidates are proposals, not facts. You batch-approve the obvious ones, filter by component to work area-by-area, reject the noise, and reset when a pass goes sideways. Nothing lands in your feature graph until you say so. Re-scanning a repo that’s already tracked? Apply enriches matching features in place instead of duplicating them.
Apply with links intact
When you apply approved candidates, Zensu doesn’t create empty records — it auto-links the tests, docs, and source files it found, so a freshly adopted feature arrives already connected to the code that implements it. The import is transactional and resilient: a duplicate doc or a colliding link is coalesced, not a reason to roll back the whole batch.
Then it drafts your journeys
Features alone don’t open the release gate. After apply, ghost-scan derives user journeys from the new features — the critical paths a user actually takes — and runs a health check on them. That’s what lets a brownfield import clear Zensu’s journey-health gate instead of stalling the moment you try to ship.
From there the normal lifecycle takes over: classify security, fill test gaps, document what’s bare, gate releases.
Adoption becomes incremental. You don’t stop the world to onboard a tool — you let it map what you’ve already built, one reviewed batch at a time.