Nummervalidatie is de routine die beslist of een reeks tekens mag staan voor een rekening, een document of een product. Het is niet één test maar drie, toegepast in een vaste volgorde: is elk teken toegestaan, heeft de reeks de juiste lengte, en komt het afsluitende cijfer overeen met de rekensom van de tekens ervoor.
Elke laag vangt een ander soort fout, en elke laag beantwoordt een veel smallere vraag dan de meeste mensen aannemen. Deze gids loopt de drie lagen in volgorde langs, legt uit waarom een geslaagde controle geen bewering over de werkelijkheid is, en laat zien waar de vier mogelijke uitspraken van een validator vandaan komen.
Wat is nummervalidatie?
In de eenvoudigste vorm is validatie een filter dat invoer die een systeem kan verwerken scheidt van invoer die het niet kan verwerken. Het filter is gebouwd op gepubliceerde regels in plaats van geheimen, en daarom kan dezelfde controle in een browser, in een nachtelijke importtaak en naast een gedrukt label draaien zonder dat ze het oneens worden.
Het woord wordt vaak opgerekt om twee ongerelateerde activiteiten te dekken. De ene is structureel: volgt deze reeks het formaat dat het schema voorschrijft? De andere is feitelijk: is dit nummer ooit uitgegeven, en aan wie? Alleen de eerste hoort bij een validator. De tweede vereist een opzoeking in het register dat de waarde heeft uitgegeven, en een offline routine kan dat niet doen.
Die twee uit elkaar houden is het hele doel van de oefening. Een formulier dat een geslaagde structuur rapporteert als een goedgekeurde identiteit, laat onzin met vertrouwen door, en de gebruiker zal het geloven.
Elk nummer en elke reeks die in dit artikel wordt beschreven is een bewust geconstrueerde illustratie, alleen geschreven om te laten zien hoe de drie lagen zich gedragen. Geen ervan staat voor een echte rekening, een echt document of een echt pakket, en een geslaagde controle in een illustratie is nooit bewijs dat zo’n registratie bestaat.
Drie lagen van filtering: tekenset, lengte en controlecijfer
De lagen zijn goedkoop om te draaien, en elke laag is blind voor de fouten die de andere vangen.
| Laag | Wat ze vraagt | Wat ze vangt | Wat ze mist |
|---|---|---|---|
| Tekenset | Zijn alle tekens hier toegestaan? | Letters getypt in een numeriek veld, losse symbolen, opmaaktekens die elders vandaan zijn geplakt | Een verkeerd cijfer dat zelf toegestaan is |
| Lengte | Heeft de reeks de omvang die het schema toestaat? | Een teken dat tijdens het typen is weggevallen of herhaald | Een reeks van dezelfde lengte waarin twee buren zijn omgewisseld |
| Controlecijfer | Volgt het afsluitende cijfer uit de rest? | De meeste fouten van één teken en veel aangrenzende verwisselingen | Elke waarde die nooit is uitgegeven |
Volgorde is net zo belangrijk als inhoud. Normaliseer eerst, controleer dan de tekenset, dan de lengte, en voer pas daarna de rekensom uit. Een routine die een controlecijfer berekent voordat spaties zijn verwijderd, weigert waarden die volkomen goed zijn, en doet dat met een melding die de gebruiker op een probleem wijst dat niet bestaat.
Waarom maakt het passeren van het formaat een nummer niet echt?
Een controlecijfer is een rekenkundige samenvatting van de tekens die eraan voorafgaan. Het wordt uitsluitend uit die tekens berekend, dus het bewijst interne consistentie en niets daarbuiten. Iedereen die de gepubliceerde regel begrijpt, kan een reeks produceren die eraan voldoet, en dat is precies wat een generator met opzet doet.
Wat de controle niet kan zien, is het register. Of een rekening open is, of een document ooit is gedrukt, of een product ooit is verpakt — dat alles leeft in een database onder een autoriteit waar de validator geen toegang toe heeft. Een waarde kan aan elke offline laag voldoen en toch helemaal nergens op slaan; de gids over controlecijfers werkt uit wat dat in het bijzonder voor identificatieschema’s betekent.
Behandel een uitspraak als een bewering over de reeks, nooit over de werkelijkheid. Die manier van kijken houdt foutmeldingen eerlijk en weerhoudt beoordelaars ervan meer in een groen vinkje te lezen dan het kan dragen.
Eén nummer kan tot meerdere schema’s behoren
Schema’s overlappen. Twee onafhankelijke nummerstelsels kunnen het eens zijn over de toegestane tekenset, de totale lengte en zelfs de rekensom van het afsluitende teken, zodat dezelfde reeks een waar lid van beide is. Daar is niets mis mee; het is wat er gebeurt wanneer afzonderlijke ontwerpers naar vergelijkbare conventies grijpen.
Een validator die één geraden land aankondigt, verbergt de dubbelzinnigheid en verzint informatie die hij niet heeft. Een betere interface somt elk schema op waaraan de reeks werkelijk voldoet en laat de lezer beslissen welk register daarna te raadplegen. Dezelfde redenering werkt omgekeerd wanneer niets overeenkomt: het eerlijke antwoord is dat geen enkele geïmplementeerde regel de invoer herkent, niet dat de waarde onwaar is. Een volkomen echt nummer kan eenvoudigweg buiten de verzameling regels vallen die een hulpmiddel kent, en dat is precies het onderwerp van nummers zonder controlecijfer.
Normalisatie: spaties, streepjes en hoofdletters
Echte invoer komt geformatteerd voor menselijke ogen. Rekeningnummers worden in groepen gedrukt, identiteitswaarden dragen punten en schuine strepen, en labels mengen hoofd- en kleine letters. Niets daarvan hoort bij het nummer, en het moet allemaal weg voordat er ook maar iets wordt vergeleken.
Normalisatie verwijdert de scheidingstekens, voegt reeksen witruimte samen en brengt letters naar één vorm. Het effect is dat twee verschillend geformatteerde kopieën van één waarde dezelfde reeks worden, en dat maakt duplicaatdetectie en gelijkheidstests pas zinvol.
Twee waarschuwingen zijn het onthouden waard. Normaliseren is geen reparatie, want het verwijdert presentatie in plaats van fouten, dus het zal een verkeerd getypt teken nooit redden. En het is ook geen beveiligingsmaatregel: een routine die genormaliseerde reeksen vergelijkt, vergelijkt nog steeds niet-vertrouwde invoer.
Voor ontwikkelaars: hoe je een validatiepijplijn opzet
Modelleer de pijplijn als een reeks zuivere stappen die elk een resultaat samen met een reden teruggeven, in plaats van als één boolean die elk onderscheid opslokt.
- Normaliseer de ruwe invoer en bewaar de genormaliseerde vorm naast het origineel.
- Controleer de tekenset en weiger alles daarbuiten voordat er een rekensom draait.
- Controleer de lengte tegen het schema dat de aanroeper heeft gekozen.
- Bereken het controlecijfer en vergelijk het.
- Geef een uitspraak terug die een mislukte controle onderscheidt van een onbekend schema.
Bewaar de reden, niet alleen de uitkomst. Een veld dat alleen zegt dat de waarde ongeldig is, dwingt de gebruiker te raden, terwijl een veld dat zegt dat het formaat klopte maar het afsluitende teken niet, vertelt wat er moet veranderen. Waar helemaal geen regel voor de waarde bestaat, zeg dat ronduit in plaats van de faaltekst te hergebruiken; het overzicht van controlecijferalgoritmen laat zien hoeveel verscheidenheid achter de laatste laag schuilt, en als het veld een kaartnummer bevat, horen de kaartspecifieke regels bij de gids over het Luhn-algoritme en niet hier.
Houd de regels ten slotte als data bij. Wanneer een schema zijn lengte of zijn rekensom wijzigt, moet een update een wijziging zijn in een beschrijving van de regel, niet in de logica die hem leest.
Volgende stappen
Neem één numeriek veld in je product en schrijf op welke van de drie lagen het nu bewaakt. Plak dan een waarde die aan het formaat voldoet maar de rekensom niet haalt in de nummervalidatietool en lees de uitspraak die hij teruggeeft; het verschil tussen een mislukte controle en een onbekend schema is het onderscheid dat de meeste formulieren nog steeds vervagen.