Skip to content

Comparison

Base64 vs. base64url: zwei Zeichen, die zählen

Dasselbe Alphabet, andere letzte zwei Zeichen, anderes Padding. Einzeiliger Unterschied, völlig andere Einsatzgebiete.

By Published

Kurzfassung. Base64 und base64url sind dieselbe Kodierung, abgesehen von drei in RFC 4648 definierten Details: + wird zu -, / wird zu _, und das Padding = entfällt. Verwenden Sie base64url überall dort, wo der kodierte Wert in einer URL, einem JWT oder einem signierten Cookie unterwegs ist; verwenden Sie Standard-Base64 für E-Mail-Anhänge, HTTP Basic Auth und Data-URIs.

Beide sind in RFC 4648 definiert. Standard-Base64(§4) und base64url(§5) unterscheiden sich in genau drei Details: zwei Alphabet-Ersetzungen und die Behandlung des Paddings. Das war’s. Aber sie zu verwechseln zerstört JWTs, signierte Cookies und alles andere, was in einer URL unterwegs ist.

Der Unterschied

EigenschaftStandard-Base64Base64url
62. Zeichen+-
63. Zeichen/_
Padding= auf Vielfaches von 4Typischerweise weggelassen
URL-sicher?Nein (+, /, = brauchen Prozentkodierung)Ja
Definiert inRFC 4648 §4RFC 4648 §5

Dieselbe Eingabe, beide Kodierungen

Kodierung von https://example.com/?q=hello world:

  • Standard: aHR0cHM6Ly9leGFtcGxlLmNvbS8/cT1oZWxsbyB3b3JsZA==
  • Base64url: aHR0cHM6Ly9leGFtcGxlLmNvbS8_cT1oZWxsbyB3b3JsZA

Beachten Sie, dass aus dem / in der Standardform ein _ in base64url wird und das nachgestellte == entfällt.

Warum URLs ihre eigene Variante brauchen

Das Standard-Base64-Alphabet enthält + und/. Beide sind in der URL-Syntax reserviert:

  • / ist der Pfadtrenner.
  • + wird per Konvention in formularkodierten Query-Strings als Leerzeichen interpretiert.
  • = ist der Schlüssel-Wert-Trenner in Query-Strings.

Einen Standard-Base64-String in eine URL einzubetten erfordert die Prozentkodierung aller drei: +wird zu %2B, / wird zu%2F, = wird zu %3D. Der String wird länger und schwerer lesbar. base64url vermeidet die Prozentkodierung, indem es Zeichen wählt, die bereits URL-sicher sind.

Warum Padding in base64url optional ist

Standard-Base64 füllt die Ausgabe stets mit = auf ein Vielfaches von 4 Zeichen auf. Das ist nicht mathematisch notwendig — der Decoder kann die ursprüngliche Länge aus der Ausgabelänge modulo 4 ableiten. Padding existiert für Streaming-Decoder, die die Grenze zwischen aneinandergereihten Chunks kennen müssen.

Base64url überspringt das Padding, weil: (a) es redundant ist, (b) = in URLs prozentkodiert werden muss und (c) nachgestellte Gleichheitszeichen in URLs mitunter Pfadparser, CDNs und Cache-Schlüssel verwirren.

Wo welche verwendet wird

EinsatzfallVariante
E-Mail-Anhänge (MIME)Standard-Base64
HTTP Basic Auth (Authorization: Basic …)Standard-Base64
Data-URIs (data:image/png;base64,…)Standard-Base64
JWT (alle drei Segmente)Base64url, kein Padding
OAuth 2.0 PKCE Code-Verifier/-ChallengeBase64url, kein Padding
WebPush-Nachrichtenschlüssel, JOSE/JWS/JWEBase64url, kein Padding
Signierte Cookies (Rails, Django usw.)Base64url, kein Padding

Die Dekodierungsfalle

Der Standard-Base64-Decoder vieler Bibliotheken scheitert an base64url-Eingaben. Pythons base64.b64decodelehnt - und _ab; Node.js’ Buffer.from(s, "base64")ist nachsichtig, doch die Umkehrung (.toString("base64")) gibt Standard-Base64 aus.

Sprachübergreifende Tricks: vor dem Dekodieren ersetzen.

// base64url → standard Base64
const standard = base64url
  .replace(/-/g, "+")
  .replace(/_/g, "/")
  .padEnd(Math.ceil(base64url.length / 4) * 4, "=");

Besser: Verwenden Sie eine Bibliothek, die base64url explizit unterstützt (Node 16+ hat Buffer.from(s, "base64url"); Python hat base64.urlsafe_b64decode).

Die pragmatische Regel

Wenn der kodierte Wert in einer URL, einem JWT, einem signierten Cookie oder als Pfadsegment erscheint — verwenden Sie base64url. Wenn er für einen E-Mail-Anhang, einen HTTP-Header (außer Cookies) oder eine JSON-Data-URI ist — verwenden Sie Standard-Base64.

Unser Base64-Encoderbeherrscht beide Varianten, mit einem Umschalter für das Alphabet. Der JWT-Decoder nimmt base64url an, weil der Standard es verlangt.

Zahlenfakten

  • Kodierte Länge: beide Varianten dehnen Binärdaten um genau 4/3 (ceil(n/3)*4). 100 Eingabebytes → 136 Ausgabezeichen in Standard-Base64 oder 134 Zeichen ohne Padding in base64url.
  • Padding-Overhead: Standard-Base64 fügt pro kodiertem String 0, 1 oder 2 =-Zeichen hinzu — höchstens 1,5 % Größenaufschlag bei kurzen Nutzdaten, vernachlässigbar bei langen.
  • Prozentkodierungskosten in URLs: jedes + / = in Standard-Base64 dehnt sich beim URL-Kodieren auf 3 Bytes (%2B %2F %3D) aus. Bei einem 512-Zeichen-JWT sind das typischerweise 30–60 verschwendete Bytes — base64url vermeidet es vollständig.
  • Alphabetgröße: 64 Zeichen in beiden, also trägt jedes Ausgabezeichen genau 6 Bit Eingabe.
  • JWT-Segmentgrößen (RFC 7519): typischer Header 40–50 Zeichen, Payload 100–400 Zeichen, HS256-Signatur 43 Zeichen (genau 32 Bytes / 6 = 43 base64url-Zeichen, ohne Padding).
  • Durchsatz: Node 20 Buffer.from(s, "base64") dekodiert mit ~2 GB/s; Python base64.b64decode mit ~600 MB/s auf einem Laptop von 2024.

Entscheidungsmatrix

Wo der Wert lebtWahl
URL-Pfad oder Query-Stringbase64url, kein Padding
JWT (Header / Payload / Signatur)base64url, kein Padding (RFC 7519)
OAuth 2.0 PKCE Verifierbase64url, kein Padding (RFC 7636 §4.1)
Signiertes Cookie (Rails / Django / Express)base64url, kein Padding
data:-URI in HTML/CSSStandard-Base64 mit Padding
MIME-E-Mail-AnhangStandard-Base64 mit Padding, 76-Zeichen-Zeilenumbruch (RFC 2045)
HTTP-Basic-Auth-HeaderStandard-Base64 (RFC 7617)
WebPush-Abonnementschlüsselbase64url, kein Padding (RFC 8291)

Quellen

Frequently asked questions

Kann ich base64url mit einem Standard-Base64-Decoder dekodieren?
Manchmal — Nodes Buffer.from ist nachsichtig, Pythons b64decode nicht. Der sprachübergreifend sichere Ansatz: ersetzen Sie '-' durch '+', '_' durch '/' und füllen Sie vor dem Dekodieren mit '=' auf ein Vielfaches von 4 auf. Moderne Laufzeiten bieten explizite base64url-Decoder (Node 16+, Pythons urlsafe_b64decode), die das direkt erledigen.
Warum lässt base64url das Padding weg?
Drei Gründe: Es ist mathematisch redundant (Decoder können die ursprüngliche Länge aus der Ausgabelänge modulo 4 ableiten), das '='-Zeichen muss in URLs prozentkodiert werden, und nachgestellte '=' verwirren manche Pfadparser, CDNs und Cache-Schlüssel.
Sind JWT-Segmente immer base64url?
Ja. RFC 7519 schreibt base64url ohne Padding für alle drei JWT-Segmente (Header, Payload, Signatur) vor. Ein JWT mit Standard-Base64 zu kodieren erzeugt ein Token, das in keiner konformen Bibliothek verifiziert wird.
Spart base64url Bytes gegenüber Standard-Base64?
Geringfügig — dieselbe Alphabetgröße bedeutet vor dem Padding dieselbe kodierte Länge. Das Weglassen des Paddings spart 0–2 Bytes pro Kodierung. Die eigentliche Ersparnis ist das Vermeiden der Prozentkodierung (jedes %XX sind 3 Bytes statt 1), was pro Base64-String in einer URL 6–9 Bytes sparen kann.

Related

Published May 16, 2026