VibeRepair+

Retrieval-augmented program repair for Java and Python · Jan – May 2026
With Yingjia Gu and Shengyue Guo · CS Software Engineering for GenAI, UIUC

Summary

VibeRepair+ extends a specification-centric repair paradigm to Java and Python with a hybrid retriever (Reciprocal Rank Fusion over parallel dense and lexical retrievers), LLM-based distillation of fix guidance, and removal of an external tool dependency — cutting token consumption from 1,564 to roughly 150 tokens per query.

My part of the work was the retriever framework and the evaluation. The evaluation is the part I would most want a reviewer to read, because the headline result is that the protocol everyone was using could not distinguish the retrievers at all.

A framework where adding a retriever is one file

The retriever layer sits over a 97,402-example Java bug-fix corpus. Adding a retrieval strategy requires one Python file and zero changes to the serving endpoint, the evaluation harness, or the metrics. Reproducibility is enforced by a SHA-256 fingerprint over the corpus and a locked holdout split, so two runs that report different numbers cannot be silently reading different data.

Three retrievers are compared under it: a dense embedding baseline (ada, ~285 ms p50), lexical BM25-Okapi, and a hybrid that runs both in parallel and fuses by RRF rank summation with k = 60.

The evaluation was measuring a self-match

The incumbent protocol is leave-one-out over the corpus: hold out an example, query with it, check whether its own fix comes back. Under it, all three retrievers score a perfect recall@1 = 1.000 and MRR@10 = 1.000. That looks like a solved problem.

It is an artifact. After excluding the self-match, the retrievers agree on only 34.1% of top-1 results, with a top-10 Jaccard of 0.166 — three systems returning substantially different evidence, all scoring identically. LOO was measuring whether a document can find itself, which every retriever can do.

The replacement protocol:

  • External queries. 521 real Defects4J bugs, none drawn from the corpus (533 minus a leak filter, an empty-delta case, and 11 lacking annotations).
  • Operator-aware proxy ground truth. Unified diffs with Jaccard overlap over tokens, with operators preserved — recovering 170 of 171 bugs that a word-only tokenizer left with empty deltas because the fix was operator-only (==!=). The top-5 corpus rows by Jaccard form the positive set.
  • A two-stage leak check (embedding cosine > 0.95 and normalized Levenshtein > 0.95), which finds zero byte-overlap — the evaluation is genuinely external.
  • A random-retrieval floor reported alongside everything: recall@10 ≈ 5×10-4, so the dense baseline at 0.138 is a 276× improvement over chance and the task is meaningfully discriminative even where absolute numbers look low.

Results under the corrected protocol

External-query retrieval on 521 Defects4J bugs. All three score self-LOO recall@1 = 1.000; that gap is the point.
Retrieverr@1r@5r@10MRRnDCGp50 latency
ada (dense).083.109.138.097.044285 ms
BM25 (lexical).085.138.177.111.0553,756 ms
Hybrid RRF (k = 60).086.154.190.114.0554,247 ms

Lexical beats dense here, by 27.8% relative

BM25 outperforms the dense baseline on all five quality metrics; binary recall@10 is 0.177 vs. 0.138, a +27.8% relative gain (Δ = +0.038, above the ±0.02 standard-error band at N = 521). This inverts the usual dense-beats-lexical assumption, and the reason is domain-specific: Java bug-fix patterns are dominated by API names, class paths, and method signatures — exactly the rare tokens BM25's IDF weighting is built for. The quality comes at a 13× latency cost, and BM25's p99 of 38.5 s exceeds a typical ~30 s LLM-agent per-turn budget, which matters for deployment even though it never shows up in a quality table.

The hybrid's value is per-bug, not in the average

Hybrid RRF leads five of six metrics, but its Δ = +0.013 over BM25 sits inside the standard-error band — so the aggregate is not the evidence. The per-bug decomposition is:

Per-bug top-10 hit decomposition, 521 Defects4J bugs.
Bucket (top-10 hit)CountFraction
All three530.102
BM25 + hybrid only240.046
ada + hybrid only70.013
ada + BM25 only10.002
BM25 only140.027
ada only110.021
Hybrid only (unique RRF gain)150.029
Missed by all three3960.760
ada ∪ BM25 oracle ceiling1100.211

15 bugs are hit by the hybrid and missed by both sub-retrievers: cases where the positive sits at rank 11–100 for one retriever and RRF surfaces it by summing tail-rank evidence from both top-100 candidate lists. The hybrid realizes 84 of the 110 oracle hits (76.4%); the remaining 24% is the cost of RRF's fairness property, and points at a cascade architecture as the next ablation.

End-to-end repair

On a Defects4J v1.2 subset with Qwen Coder 2.5, VibeRepair+ improved plausible repair rates over the original VibeRepair in all four tested project categories: Chart 53% → 75%, Closure 22% → 43%, Lang 63% → 68%, Math 49% → 55%. The Python port repairs 26 of 30 BugsInPy single-function bugs (87%).

← Back to home