Regex Finnish personal identity code (henkilötunnus)
A henkilötunnus is written '131052-308T': DDMMYY, a century sign, 3 digits and a check character (the remainder modulo 31 of DDMMYY+NNN, from a 31-character table without G, I, O, Q, Z). Since 1 January 2023 (Decree 690/2022), the sign is 'A' to 'F' for births since 2000, '-' or 'Y, X, W, V, U' for 1900-1999, and '+' for 1800-1899. validator.js (tax ID validation) still knows only '-', '+' and 'A': it rejects '010594Y9021', '010516B903X' and anyone born since 2000 with a B to F sign. Here's a pattern coupling the sign to the last two digits of the year, compared against those three real attempts.
/^(?:0[1-9]|[12][0-9]|3[01])(?:0[1-9]|1[0-2])(?:[5-9][0-9]\+|[0-9]{2}[-U-Y]|[012][0-9][A-F])[0-9]{3}[0-9A-FHJ-NPR-Y]$/passes 25/25 cases
Comparison of existing patterns
| Source | pattern | Score on the corpus | ReDoS |
|---|---|---|---|
| validator.js (fi-FI, implémentation de la validation des identifiants fiscaux) — signe limité à « - », « + » et « A » : rejette tout signe B-F et U-Y introduit en 2023 ; drapeau i accepte les minuscules ; mois 99 et jour 00 passent (la date est testée ensuite) | ^\d{6}[-+A]\d{3}[0-9A-FHJ-NPR-Y]$ | 18 / 25 | safe |
| finnish-ssn (npm, ~95 000 téléchargements/mois) — la meilleure sur les signes (couple le signe à l'année, jour et mois bornés) mais « [\dA-Z] » accepte I, O, Q, Z comme caractère de contrôle (« 131052-308I » passe) ; la clé est vérifiée dans le code | ^(0[1-9]|[12]\d|3[01])(0[1-9]|1[0-2])([5-9]\d\+|\d\d[-U-Y]|[012]\d[A-F])\d{3}[\dA-Z]$ | 23 / 25 | safe |
| Microsoft Presidio (détecteur de données personnelles) — signes à jour mais « \d{6} » : aucune contrainte de date (mois 00, jour 32 passent) ; non ancrée avec \b, conçue pour repérer un code dans un texte | \b(\d{6})([-+ABCDEFYXWVU])(\d{3})([0123456789ABCDEFHJKLMNPRSTUVWXY])\b | 22 / 25 | safe |
Implementation
const re = new RegExp("^(?:0[1-9]|[12][0-9]|3[01])(?:0[1-9]|1[0-2])(?:[5-9][0-9]\\+|[0-9]{2}[-U-Y]|[012][0-9][A-F])[0-9]{3}[0-9A-FHJ-NPR-Y]$", "");
re.test(input);Limits
- Valide seulement la FORME : ne calcule pas le caractère de contrôle (modulo 31) ni le nombre de jours du mois. « 131052-308U » (mauvaise clé), « 310252-308Y » (31 février) et « 290299-123U » (29 février 1999) ont la bonne forme et passent ce motif.
- Le signe est couplé aux deux derniers chiffres de l'année : « + » années 50-99, A-F années 00-29, « - » et U-Y toutes années. « 131052A308T » (2052 avec A) est donc rejeté, et il faudra élargir le motif en 2030 ; les naissances de 1800 à 1849 ne sont pas couvertes.
- Le numéro individuel 002 à 899 est la plage d'usage courant selon la DVV ; la plage 900-999 est temporaire ou de test : le motif l'accepte. Le calcul de la clé ne dépend pas du signe : « 131052-308T » et « 131052Y308T » partagent le même contrôle.
- Majuscules seulement : « 131052a308t » est rejeté. Le motif ne tolère aucun espace. N'utilisez jamais de vrais numéros d'identité dans vos tests ; les exemples viennent de la DVV et des suites de tests de finnish-ssn.