[COMPARE] Base64 vs Base64URL vs Base32
Trois encodages, une seule RFC. Voici ce qui diffère vraiment — alphabet, surcoût, lisibilité, sensibilité à la casse — et comment choisir le bon pour les URL, noms de fichiers, e-mails, codes QR et codes prononcés à voix haute.
// LE TABLEAU COMPARATIF RAPIDE
Base64 Base64URL Base32
(RFC 4648 §4) (RFC 4648 §5) (RFC 4648 §6)
────────────────────────────────────────────────────────────────
Alphabet size 64 64 32
Bits per char 6 6 5
Characters used A-Z a-z 0-9 A-Z a-z 0-9 A-Z 2-7
+ / - _ (+ = for pad)
Padding = (required) = (optional) = (optional)
Case-sensitive Yes Yes No (A = a)
Size overhead ~33% ~33% ~60%
URL-safe No Yes Yes
Filename-safe No Yes Yes
DNS-safe No Yes Yes
Human-readable Medium Medium High
Human-spoken Painful Painful Doable
QR-code friendly OK OK Excellent
(alphanumeric) (alphanumeric) (alphanumeric mode)
// CE QU'ILS ONT EN COMMUN
Les trois sont définis dans la RFC 4648 — un unique document de 2006 qui a unifié la famille des « encodages binaire-vers-texte base-N ». Ils partagent le même algorithme sous-jacent : prendre une entrée binaire, regrouper les bits en blocs de log₂(taille de l'alphabet), mapper chaque bloc à un caractère, compléter pour s'aligner sur la frontière du mot de sortie.
• Base64 : blocs de 6 bits → 4 caractères pour 3 octets (rapport 4/3, environ 33 % plus grand)
• Base32 : blocs de 5 bits → 8 caractères pour 5 octets (rapport 8/5, environ 60 % plus grand)
• Base16 (hex) : blocs de 4 bits → 2 caractères pour 1 octet (rapport 2/1, 100 % plus grand)
Les trois sont réversibles, déterministes, et préservent chaque octet d'entrée. Ce sont des encodages, pas de la compression ni du chiffrement. Quiconque possède la chaîne peut la décoder.
// QUAND CHOISIR BASE64 (STANDARD, §4)
Le Base64 standard est le choix par défaut pour tout canal textuel qui n'est pas une URL. Les corps d'e-mail MIME, les certificats enveloppés en PEM, HTTP Basic Auth, S/MIME, XML-DSIG, les data URI, et la plupart des conteneurs binaire-dans-texte de formats de fichiers l'utilisent. Les caractères + / = sont tous sûrs à l'intérieur des valeurs d'attribut entre guillemets, dans les en-têtes d'e-mail (avec retour à la ligne), et dans les chaînes XML/JSON.
Utilisez le Base64 standard lorsque le consommateur en aval est un protocole textuel qui accepte des caractères ASCII imprimables arbitraires — et tout particulièrement lorsque les spécifications de niveau RFC le mentionnent explicitement (MIME : RFC 2045 ; PEM : RFC 7468 ; HTTP Basic Auth : RFC 7617 ; data URI : RFC 2397).
- > Pièces jointes d'e-mail (encodage de transfert base64 MIME)
- > Certificats, clés, CRL au format PEM (-----BEGIN ... -----)
- > Valeur de l'en-tête d'authentification HTTP Basic
- > Data URIs : data:image/png;base64,...
- > Charges utiles S/MIME et XML-ENC
- > Signatures SOAP / XML-DSIG classiques
- > Tout champ binaire à l'intérieur d'un document JSON qui n'est pas ensuite placé dans une URL
// QUAND CHOISIR BASE64URL (§5)
Dès que votre sortie Base64 touche une URL, une valeur de cookie, un nom de fichier, une étiquette DNS, ou tout endroit où + / = devrait être encodé en pourcentage, passez à Base64URL. Il utilise le même alphabet de 64 caractères avec deux échanges (+ → -, / → _) et supprime conventionnellement le remplissage.
- > Jetons JWT — en-tête, charge utile, signature sont tous en base64url (RFC 7515)
- > OAuth 2.0 PKCE code_challenge (RFC 7636)
- > Paramètres OpenID Connect state et nonce
- > Liens magiques, jetons d'invitation, jetons de réinitialisation de mot de passe
- > Valeurs de cookies qui peuvent être copiées dans des URL
- > Noms de fichiers dérivés de hachages — évitez / dans les noms de fichiers
- > Étiquettes DNS, enregistrements TXT — tirets autorisés, barres obliques non
- > Clés de stockage adressable par contenu
- > Identifiants courts d'URL générés à partir d'octets aléatoires
// QUAND CHOISIR BASE32 (§6)
Base32 n'utilise que 32 caractères : majuscules A–Z et chiffres 2–7. C'est environ 60 % de surcoût de taille — bien pire que Base64 — mais vous gagnez trois propriétés très spécifiques que Base64 ne peut pas égaler.
Insensibilité à la casse. L'alphabet est uniquement en majuscules. Les humains qui lisent ou tapent la chaîne peuvent ignorer la casse ; JBSWY3DP et jbswy3dp se décodent à l'identique.
Caractères désambiguïsés. Les chiffres 0, 1, 8 et 9 sont exclus parce qu'ils ressemblent à O, I, B et g dans les polices courantes. Seuls 2–7 sont utilisés. Cela rend la transcription humaine depuis une page imprimée ou un écran de téléphone beaucoup plus fiable.
Compatibilité avec le mode alphanumérique des codes QR. Les codes QR ont un mode « alphanumérique » spécial qui encode 5,5 bits par caractère en utilisant un sous-ensemble d'ASCII. Base32 tient entièrement dans ce sous-ensemble (plus le remplissage), donc une chaîne Base32 encodée en QR est nettement plus petite qu'une chaîne Base64 encodée en QR.
- > Graines de secret TOTP / HOTP — Google Authenticator, 1Password, Authy utilisent tous Base32
- > Adresses Tor .onion v3 — encodages Base32 de 56 caractères de clés ed25519
- > Hachages d'infos BitTorrent partagés sous forme de liens magnet
- > Codes de localisation partageables humainement de type géohash
- > Clés de licence et numéros de série de produits
- > Codes de récupération imprimés (codes de sauvegarde 2FA, mnémoniques de portefeuille)
- > Transcription de type DTMF sur canaux vocaux
- > Systèmes qui nécessitent un stockage insensible à la casse (étiquettes DNS)
// SURCOÛT DE TAILLE — UN EXEMPLE CONCRET
// Input: a 32-byte SHA-256 hash
// Raw: 0x89abcdef… (32 bytes, binary — can't put in text)
// Hex (Base16): 40b2e2… (64 chars, 100% overhead)
// Base32: 5ENM4H2TQWMZ3O4OQBJAFY5Q (56 chars, 75% overhead)
// Base64: ia+N7/eZtRsPj5TqFoqUlD… (44 chars, 37% overhead)
// Base64URL: ia-N7_eZtRsPj5TqFoqUlD… (43 chars, 34% overhead, no padding)
// Input: a 16-byte UUID
// Hex: e7a6c1d0-4b7d-4c6c-8e2f-9f1a3e4b5c6d (36 chars incl. dashes)
// Base32: 5WTMDUCLPVGGZDRPTF… (26 chars)
// Base64: 56bB0Et9TGyOL58aPktcbQ== (24 chars)
// Base64URL: 56bB0Et9TGyOL58aPktcbQ (22 chars, no padding)
// BENCHMARK DE LISIBILITÉ HUMAINE
C'est là que Base32 brille. Essayez de lire ceux-ci à voix haute :
• a+b/c1D2e3F/+g= — Base64. « a minuscule, plus, b minuscule, barre oblique, c minuscule, un, D majuscule, deux, e minuscule, trois, F majuscule, barre oblique, plus, g minuscule, égal. » Sujet à des erreurs de transcription rien que sur la casse.
• JBSWY3DPEHPK3PXP — Base32. « J-B-S-W-Y, trois, D-P-E-H-P-K, trois, P-X-P. » La casse n'a pas d'importance. Aucune ambiguïté 0/O ou 1/l. Vous pouvez lire ceci au téléphone avec une grande confiance.
C'est exactement pourquoi TOTP utilise Base32 : quelqu'un doit taper la graine dans son application d'authentification depuis un écran de repli avec code QR. La sensibilité à la casse de Base64 générerait d'innombrables tickets de support.
// COMPARAISON DE TAILLE DE CODE QR
Les codes QR disposent d'un « mode alphanumérique » spécial qui condense 5,5 bits par caractère en utilisant un sous-ensemble de 45 caractères : 0–9, A–Z (majuscules uniquement), espace, et $ % * + - . / :. Tout ce qui est hors de ce sous-ensemble force le code QR en « mode octet » qui utilise 8 bits par caractère — codes QR significativement plus grands.
Base32 est entièrement à l'intérieur du sous-ensemble alphanumérique. Base64 ne l'est pas — les lettres minuscules et +/= forcent le mode octet (en réalité +/ sont dans l'ensemble alphanumérique, mais toute minuscule force le mode octet). Cela signifie qu'une charge utile donnée tient dans un code QR plus petit lorsqu'elle est encodée en Base32 — souvent la différence entre un QR 21×21 lisible et un 33×33 encombré.
// PIÈGES DE DÉCODAGE
-
>
Sensibilité à la casse — les décodeurs Base64 rejettent une entrée mal cassée (
SGVsbG8=≠sgvSbg8=). Les décodeurs Base32 normalisent généralement en majuscules avant la recherche, donc ils tolèrent toute casse. -
>
Remplissage — le Base64 standard requiert le remplissage
=; JWT/base64url l'interdit ; Base32 le rend optionnel (RFC 4648 §6). Vérifiez toujours ce que votre décodeur attend. -
>
Espaces — le Base64 MIME est enveloppé sur 76 colonnes avec CR-LF. De nombreux décodeurs tolèrent les espaces, d'autres non. Supprimez-les avant de passer à
atob()ou son équivalent. -
>
Collisions d'alphabet — alimenter du Base64 dans un décodeur Base32 (ou inversement) semble parfois fonctionner au départ —
A,B,Csont valides dans les deux — puis échoue silencieusement en atteignant+ou=. - > Crockford Base32 est une variante non-RFC utilisée par les ID Stripe et certains systèmes blockchain. Elle utilise un alphabet différent (excluant I, L, O, U) et prend en charge les chiffres de contrôle. Ne la confondez pas avec le Base32 de la RFC 4648.
- > Base32 Extended Hex (RFC 4648 §7) — un alphabet Base32 alternatif qui préserve l'ordre de tri lexicographique. Utilisé dans les enregistrements DNSSEC NSEC3. Facile à confondre avec le Base32 standard.
// UN ORGANIGRAMME DE DÉCISION
Does the output go into a URL, cookie, filename, DNS, JWT, or OAuth flow?
│
├─ Yes → Does a human need to type or speak the string?
│ │
│ ├─ Yes → Base32 (uppercase, no ambiguous chars)
│ │ e.g., TOTP seeds, recovery codes
│ │
│ └─ No → Base64URL (more compact, URL-safe)
│ e.g., JWT, short tokens, hash-named files
│
└─ No → Does the output go into a QR code that must stay tiny?
│
├─ Yes → Base32 (fits in QR alphanumeric mode)
│
└─ No → Standard Base64
e.g., email MIME, PEM, HTTP Basic, data URI
// POURQUOI PAS BASE16 (HEX) ?
L'hexadécimal (la RFC 4648 §8 l'appelle Base16) est le repli universel. Tous les outils shell, débogueurs et protocoles le comprennent. Il est insensible à la casse, trivialement lisible par l'humain, et trivial à implémenter. Mais il double la taille de votre charge utile (100 % de surcoût), c'est pourquoi il n'est utilisé que pour de petits identifiants de longueur fixe : hachages SHA-256 (64 caractères hex = 32 octets), UUID (32 caractères hex = 16 octets), adresses MAC, adresses mémoire dans les débogueurs.
Pour tout ce qui dépasse quelques dizaines d'octets, le coût de taille de l'hex est réellement douloureux sur le fil. Base64 est 50 % plus petit que l'hex, Base32 est 25 % plus petit. C'est pourquoi Base64 a gagné les cas d'usage e-mail et embed web, tandis que l'hex est resté dans les scénarios de débogage et d'affichage de hachages.
// ET BASE58 / BASE62 / BASE85 ?
Des encodages base-N non-RFC existent pour des niches spécifiques :
• Base58 — adresses Bitcoin, ID de photos Flickr. Exclut les quatre caractères ambigus (0, O, I, l) et +/ pour faciliter la transcription humaine. Environ 37 % de surcoût.
• Base62 — raccourcisseurs d'URL, ID snowflake Twitter. N'utilise que des alphanumériques (aucun caractère spécial), sûr dans les URL sans échappement. Environ 34 % de surcoût.
• Base85 / Ascii85 / Z85 — PostScript, PDF, anciennes trames ZeroMQ. Environ 25 % de surcoût (plus dense que Base64) mais avec des choix de caractères délicats qui peuvent causer un enfer d'échappement XML/JSON.
Ces derniers sont intéressants, mais ils ne sont pas standardisés par la RFC 4648. Si vous livrez un protocole public, Base64 ou Base64URL est presque toujours la valeur par défaut la plus sûre car la bibliothèque standard de chaque langage les prend déjà en charge. Si vous choisissez Base58, vous livrerez une dépendance à chaque consommateur.
// ESSAYEZ-LES CÔTE À CÔTE
• Encodeur Base64 — alphabet standard avec un interrupteur URL-safe
• Encodeur Base64URL — URL-safe avec remplissage supprimé
• Encodeur Base32 — alphabet RFC 4648 §6
• Encodeur Base16 (hex) — à titre de comparaison
• Encodeur Base58 — alphabet convivial de style Bitcoin
Lectures complémentaires :
• Qu'est-ce que le Base64 et comment fonctionne-t-il ?
• URL-safe vs Base64 standard — l'histoire complète
• Base64 pour UTF-8 et Unicode