Code health
Know which code will break next, and the fix for it.
Every file scored for defect risk, maintainability and performance. Then a ranked worklist: named refactoring plans with the tests to run, slow code traced across files, and dead code you can delete safely.
No LLM in the analysis · the same code always scores the same

repowise-dev/repowise · Code Health, 4,535 files
Measured, not claimed
- 0.74
- AUC predicting which files get a bug fix next
- n = 2,826 · 21 repositories, 9 languages, 2,826 files · 2026-08
- 2.3x
- more defects found under the same review budget
- n = 2,770 · p = 0.003 · 2,770 files scored by both tools at the same leakage-free commit · 2026-08
- 3.3x
- lift on a repo's own lowest-scoring files
- 16 of the 20 lowest-health files had a bug fix in the prior six months
- 7
- named refactoring plan types
- Beside 25 defect markers and 22 performance markers
Sound familiar?
Every tool says everything is wrong.
- 01
The linter flags five thousand things.
- 02
Big files always look worst, whether or not they break.
- 03
We know the file is bad. Nobody knows what to do first.
What makes it different
From a score to the next edit.
- Defect risk
A 1 to 10 score checked against real bug fixes.
Weights learned from a defect corpus, with hotspot health and the worst file kept beside the average.
- Fix first
One ranked list of what to do this week.
Each item is a first edit, its expected gain, its effort and the command that checks it.
- Refactoring plans
Seven named plans, not a vague smell.
Extract Method, Extract Class, Extract Helper, Move Method, Split File, Break Cycle and Performance Fix.
- Dataflow-checked
Extract Method that keeps behaviour.
A span is offered only when every value it returns is written on every path and no handler changes.
- Performance
N+1 queries and blocking calls, traced across files.
The loop and the I/O call can sit three calls apart. Kept separate from the defect score.
- Dead code
Delete with confidence.
Unused files, exports and packages in confidence tiers, with the ones that are safe to delete marked.
In depth
Not just a score. The next edit, ready to make.
Fix first
One ranked list of what to fix, across every signal.
Refactoring plans, performance fixes and the strongest findings compete in one queue, ranked by expected gain for effort. Each item carries its first edit and the command that checks it, so the top of the list is a task, not a topic.
- Now, next, later
- Ordered by gain, confidence and effort.
- Verify built in
- The tests that reach the code, as a command.
- Noise left out
- Tests, generated code and tiny wins are counted, not listed.
- Hotspots first
- The code you change most rises to the top.
$ repowise healthFix first (3 of 41 eligible items) 1. Extract the retry branch from parse_config now · effort M · +1.4 src/config/loader.py:212 CCN 47 and nesting 6 in a file changed 19 times this quarter. verify: pytest tests/unit/test_loader.py 2. Batch the customer lookup in enrich_orders now · effort S services/orders.py:88 · N+1, runs per request 3. Split OrderService into 3 classes next · effort L · +0.9 services/orders.py · LCOM4 3, 41 methods Code health 7.4/10 [Good] · Hotspot 6.1 · Worst 2.3 (src/config/loader.py)Refactoring plans
Seven named plans, and an Extract Method that keeps behaviour.
A plan names the change: the groups a god class splits into, the method that belongs in another class, the one import edge that breaks a cycle, the lines to lift into a helper with its parameters and return value. Extract Method is dataflow-checked, so a span is offered only when the extraction provably keeps behaviour.
- Extract Method
- The span, the helper's signature, the call that replaces it.
- Extract Class
- The cohesive groups a god class splits into.
- Move Method, Extract Helper
- Where a method belongs; one helper for every copy.
- Split File, Break Cycle
- Which symbols go where; the edges to invert.
Lift lines 214 to 241 out of parse_config
high confidenceeffort Sdef _build_retry_policy(raw: dict, attempts: int) -> RetryPolicy: ... # 28 lines, 6 decision points policy = _build_retry_policy(raw, attempts)Dataflow checked
- Every returned value is written on every path
- No state carried across loop iterations
- No local a closure shares across the span's edge
- The try stays with its handlers
tests/unit/test_loader.py::test_retry_defaultsHand to your agent
Copy the plan as a recipe. The edit, the checks, and what it must not change.
Performance
Slow code traced across files, not just inside one function.
A database call inside a loop is easy to spot when both sit in one function. Repowise follows the resolved call graph up to three hops, so it finds the loop in the service that calls the query in the repository, says whether the loop grows with the data, and groups findings that share one fix.
- N+1 and I/O in loops
- Database, network, file system and subprocess.
- Blocking calls in async
- Blocking I/O and serial awaits on the hot path.
- Per request first
- Loops that run per request outrank cold paths.
- One fix, many sites
- A shared plan when every site reaches one sink.
list_orders routes/orders.py:31
GET /orders · per request
enrich_orders services/orders.py:88
for order in rows (grows with the data)
get_customer db/customers.py:14
SELECT ... WHERE id = ? (database)
get_customers(ids) and call it once before the loopenrich_orders · services/orders.py:88
One query per order, on every request. Kept apart from the defect score.
Dead code
Delete what nothing uses, starting with what is safe.
Files nothing imports, exports nothing uses and packages nothing depends on, each with a confidence and the evidence behind it. The deletion-ready ones are marked, and entry points, framework routes and registered handlers are never reported.
- Confidence tiers
- High, medium and a review tier you opt into.
- Safe to delete
- High confidence, no runtime-load path.
- Evidence attached
- Why each finding is in, and what capped it.
- Graph plus history
- No LLM, computed during every index.
| Finding | Confidence | Ready |
|---|---|---|
| formatLegacyDateunused_export | 100% | ✓ safe |
| toCsvRowunused_export | 100% | ✓ safe |
| src/legacy/parser.tsunreachable_file | 100% | review |
| config/feature_flags.pyunreachable_file | 40% | review |
Safe to delete
2 unused exports, 24 lines. High confidence, no runtime-load path.
On a real repository
Every plan on one board, ranked.
The refactoring board plots every structural plan by how big the file is and how much code imports it, then lists them in the order to do them, each with its effort and confidence. Open one and its drawer shows the steps, the tests that reach the code and a prompt to hand to your agent.

In plain words
One number, 1 to 10, for how likely a file is to produce the next bug.
Every file starts at 10 and loses points for findings in its structure, its history and its ownership. The weights were learned from real bug fixes, so a low score has predicted defects before, and file size is controlled for, so a big file is not marked down for being big.
How to read it
What's a good score?
- 8.5 and up · Excellent
- Easy to change safely. Leave it alone.
- 7 to 8.5 · Good
- Healthy. A seven is not a warning.
- 5.5 to 7 · Fair
- Watch the trend. Refactor it if it is also a hotspot.
- 4 to 5.5 · Needs work
- Changes here are the ones that come back as bug fixes. Plan the refactor.
- Under 4 · At risk
- Where the repository's bug fixes concentrate. Start here, with the named fix.
How it works
Measure, calibrate, act.
- 01 / Measure
Extract deterministic markers
Complexity, nesting, cohesion, clones, churn, ownership, prior defects and coverage. - 02 / Calibrate
Weigh them against real defects
Offline learning against bug-fix history. Only the constants ship. - 03 / Act
Go from score to worklist
Fix first, refactoring plans, performance causes and dead code, each with the tests to run.
Where it shows up
Shows up where the work already happens.
Dashboard
The repository score, its three signals, the health map and the fix-first queue in one reading flow, with a refactoring board for every plan type.
Coding agents
One call returns a file's score, its findings and the plan to apply. The agent gets the recipe: what must hold before the edit, the steps, and the checks after.
get_health · get_dead_code
Pull requests
Every pull request shows the health of the files it touched before and after, and the new findings it introduced.
CLI
The same worklist in the terminal, and a plan printed as the prompt an agent applies.
repowise health · repowise next · repowise dead-code
Questions
What people ask before they try it.
What does the code-health score actually measure?
Every file gets a single 1 to 10 score computed from 25 deterministic markers: McCabe complexity, deep nesting, brain methods, class cohesion (LCOM4), god classes, Rabin-Karp clone detection, change entropy, co-change scatter, ownership dispersion, prior-defect history, test-quality smells, and more. Lower scores mean the file is more likely to harbor defects.
How do you know the score actually predicts bugs?
It is defect-validated. On the same 2,770 files across 9 languages with real defect labels, ranking by repowise health surfaces 2.3x the defects of a leading commercial tool under the same review budget (recall 0.173 vs 0.074, effort-aware Popt 0.607 vs 0.462, ROC AUC 0.731 vs 0.705). Across 21 open-source repos the mean cross-project ROC AUC is 0.74 with a 95% confidence interval of 0.68 to 0.79, ranging from 0.55 to 0.86 across individual repos.
Does it use an LLM?
No. Scoring is fully deterministic: 25 markers with weights calibrated offline against a defect corpus. Only the learned constants ship, so the same code always produces the same score, in under 30 seconds on a 3,000-file repo. No cloud, no API calls, no drift.
How is this different from CodeScene?
Both score code health, but repowise is open source so every heuristic is inspectable and reproducible on your own repo, and the score ships inside a broader platform: named refactoring plans your agent can apply, an architecture-aware wiki, git intelligence, architectural decisions, agent provenance, and ten MCP tools for AI agents.
Will it just flag big files?
No. The discrimination survives controlling for file size (partial Spearman rho of -0.16) and significantly out-discriminates both recent churn (+0.10 AUC) and prior-defect history (+0.12 AUC), with DeLong p below 1e-9.
Can it use my test coverage?
Yes. repowise ingests LCOV and Cobertura coverage to compute untested-hotspot risk (the intersection of low coverage and high hotspot score), alerts when a file's health starts declining, and ranks refactoring targets by impact for effort.
Can I prove these numbers on my own codebase?
Yes, that is the point. Every heuristic is open source under AGPL-3.0, and the validation runs on your own repo. On a typical project, 16 of the 20 lowest-health files had a bug fix in the last 6 months, 3.3x the 24% baseline.
Does repowise check performance?
Yes, as a static health pillar, not as an APM or profiler. repowise statically detects performance-risk shapes such as N+1 access and IO-in-loop patterns and scores them as a co-equal third pillar alongside defect risk and maintainability. It is high precision and low recall by design: it raises few findings, but the ones it raises are real. There is no runtime, no agent, and no tracing; it reads your source, like every other signal.
Does repowise refactor my code for me?
It names the refactor and hands it over. Each of the seven plan types is structured data: what moves where, the helper's signature, what else has to change and the tests to run. Your agent applies it as a recipe, or you ask for the code and get a diff to review. Nothing is ever applied to your repository on its own.
What are the seven refactoring plans?
Extract Method, Extract Class, Extract Helper, Move Method, Split File, Break Cycle and Performance Fix. Each detector reports nothing when a signal it needs is missing, so a gap means no suggestion, never a guessed one, and the same commit always gives the same plans.
How does dead code know what is safe to delete?
Every finding carries a confidence from 0 to 1 and the evidence behind it. A finding is marked safe to delete only at high confidence and with no runtime-load risk on its path, such as config, bootstrap or served assets. Entry points, framework routes and registered handlers are never reported.
Last reviewed: October 2026
Get started
See what your codebase should fix first.
Start free on a repository you know and check the lowest-scoring files against the ones that broke last quarter. For a team rollout, book a demo.