Conveya
Engineering18 februari 202612 min

5 dingen die stuk gaan in je retrieval (en hoe je ze fixt)

Chunking, recency, boosting, deduplicatie, query-rewriting. Wat wij de afgelopen 12 maanden geleerd hebben.

Ruben Vaalt
Conveya team

Retrieval-Augmented Generation (RAG) is, in elke demo die je ziet, een paar regels code: embed je documenten, embed de vraag, zoek de top-5 dichtstbijzijnde chunks, plak ze in de prompt. Dat werkt voor de demo. En dan ga je live, krijg je echte vragen, en valt het uit elkaar.

Hieronder vijf categorieën van problemen die wij in 12 maanden productie zijn tegengekomen, plus hoe we ze hebben opgelost. Geen één daarvan is rocket science; allemaal vereisen ze dat je verder gaat dan de defaults.

1. Chunking, de fout begint hier

De default in elke RAG-tutorial is recursive character splitting op 1.000 tokens met 200 overlap. Werkt voor essays. Faalt voor technische documentatie, FAQ's en juridische teksten.

Voorbeeld: een FAQ-pagina met 30 vragen. Bij 1.000-token splitting krijg je per chunk ~3-5 vragen samengevoegd. Antwoord op vraag 12 zit dan in chunk 4, samen met vraag 11 en 13, die mogelijk over heel andere onderwerpen gaan. De embedding van die chunk is een gemiddelde van drie semantisch verschillende dingen, en ranking eronder lijdt.

Onze aanpak

  • Structuur-bewust chunken. Voor Markdown splitsen we op H2, voor HTML op semantische blokken, voor FAQ-pagina's per vraag-antwoord paar.
  • Minimum-chunk-grootte. Elke chunk minstens 300 tokens, anders is de embedding te brokkelig en verlies je context.
  • Geen overlap waar het kan. Overlap is een proxy voor 'ik weet niet waar de logische grens zit'. Als je 'm wel weet (header, paragraph break), is overlap onnodig.

2. Recency, het kanaal dat niemand fixt

Pure cosine-similarity heeft geen idee dat één van twee identieke documenten van gisteren is en de andere van 2019. Voor customer support is dat een groot probleem: oude documentatie die intern gearchiveerd is maar nog in de index staat, gaat winnen van het verse FAQ-artikel als het toevallig beter aansluit op de vraag.

Onze aanpak

Een recency-boost als post-processing stap. Concreet: na de initiële vector-search vermenigvuldigen we de similarity score met een decay-functie op basis van last_modified timestamp. Documenten ouder dan 18 maanden krijgen 0.7x, ouder dan 3 jaar 0.5x. Geen harde cutoff, soms is oude doc relevant, maar genoeg om verse content de doorslag te geven bij gelijke score.

3. Authority / source boosting

Niet alle bronnen zijn gelijk. Een officiële retourvoorwaarde-pagina hoort altijd te winnen van een blog-post over retouren. Een runbook hoort te winnen van een Slack-thread. Pure similarity weet dit niet.

Onze aanpak

Per knowledge-source een authority-weight (0.5 tot 2.0). Officiele policy-pagina's: 2.0. Help-center artikelen: 1.5. Blog: 1.0. Slack-archive: 0.7. Externe sites: 0.5. Die weight wordt vermenigvuldigd met de similarity score na de vector-search.

Belangrijk: deze weights worden geconfigureerd door de merchant zelf, niet door ons. Wij weten niet welke source bij hun bedrijf gezaghebbend is. We geven defaults en ze tweaken.

4. Deduplicatie, het verborgen probleem

Veel content komt in meerdere vormen in je index: een artikel + een nieuwsbrief-versie + een Slack-doorgeef. Vector-similarity rankt ze alle drie hoog, en je top-5 retrievals zijn dan eigenlijk top-2 of top-3 unieke documenten met variaties.

Effect: de LLM krijgt 5x dezelfde info en 'denkt' dat het belangrijk is, terwijl je net die diversiteit nodig hebt om een goed antwoord te formuleren.

Onze aanpak

  1. Bij indexering: detecteer near-duplicates via MinHash / SimHash. Bewaar één canonical version per cluster.
  2. Bij retrieval: na de initial top-K vector-search, voer een diversiteit-pass. Bekend als MMR (Maximal Marginal Relevance). Resultaat: 5 retrievals die elk een ander aspect dekken in plaats van 5 variaties op dezelfde tekst.

5. Query rewriting, waar je het meeste rendement vandaan haalt

De vraag van de gebruiker is zelden de optimale zoekquery. 'Mijn pakket is kwijt' is een slechte vector-search query. 'Procedure voor verloren zending, vergoeding, contact met vervoerder' is beter.

Onze aanpak

Een kleine LLM-call vóór de vector-search die de user-query herformuleert tot 1-3 zoektermen. We gebruiken Claude Haiku, kost ~0.005 cent per call, latency 100-200ms, en de gain op retrieval-kwaliteit is significant.

const expanded = await haiku.complete({
  prompt: `Rewrite this user message as 1-3 retrieval queries.
User: ${userMessage}
Context: ${conversationHistory}
Queries (one per line):`,
});
const queries = expanded.split("\n").filter(Boolean);
const results = await Promise.all(queries.map(embedAndSearch));
// merge + dedupe + rank → return top 5

Bonus: je krijgt nu meerdere kandidaat-queries die je kunt gebruiken voor hybrid search (vector + keyword/BM25), wat in onze tests nog eens 15-20% extra relevance-winst geeft.

Wat dit ALLEMAAL niet vervangt

Goed kennisbeheer. Als je documentatie verouderd, contradictoir of onvolledig is, geen RAG-techniek redt je. De technieken hierboven maken een goede knowledge base 30-50% effectiever. Een slechte knowledge base zorgvuldiger ophalen is nog steeds slechte content ophalen.

Klaar om te beginnen?

Bouw je eerste AI-agent.

Vandaag opzetten, vanmiddag live. Met je eigen content en je eigen tools, zonder dev.

  • Gratis starten
  • Geen creditcard nodig
  • Live in een middag
Nova
Live · jouw agent
Online
Hoi! Waar blijft mijn bestelling?
Verzonden gisteravond, morgen 13-15 uur in Utrecht.
Bestelling opgezocht in Shopify·in 0,4 s
    5 dingen die stuk gaan in je retrieval (en hoe je ze fixt) | Conveya