The Base64 alphabet
· 7 min read
Base64 has exactly 64 characters, chosen so that binary data survives a trip through anything that expects text. Knowing which 64 — and which characters are deliberately absent — is what lets you look at a string and say whether it is standard Base64, the URL-safe variant, or not Base64 at all.
The 64 characters, in order
The alphabet is defined by RFC 4648 and is ordered by value, 0 through 63:
| Values | Characters |
|---|---|
| 0–25 | A B C D E F G H I J K L M N O P Q R S T U V W X Y Z |
| 26–51 | a b c d e f g h i j k l m n o p q r s t u v w x y z |
| 52–61 | 0 1 2 3 4 5 6 7 8 9 |
| 62 | + |
| 63 | / |
So A is 0, Z is 25, a is 26, 0 is 52, and / is 63. Uppercase comes first, which is why short Base64 strings so often begin with a capital letter, and why a run of zero bytes encodes as a run of As.
Why = is not the 65th character
The padding character = appears in Base64 output but is not part of the alphabet. It carries no data. It exists only to make the output length a multiple of four.
The reason is arithmetic. Base64 packs 3 bytes (24 bits) into 4 characters of 6 bits each. When the input length is not a multiple of 3, the last group is short:
| Bytes left over | Characters emitted | Padding |
|---|---|---|
| 3 (full group) | 4 | none |
| 2 | 3 | = |
| 1 | 2 | == |
You will therefore never see three = in a row, and never one in the middle of a string — only one or two, only at the end. A decoder can reconstruct the original length from the padding, which is why some parsers reject unpadded input even though the data is perfectly recoverable without it.
base64url: two characters swapped
Standard Base64 uses + and /, both of which are hostile in a URL. / is a path separator, and + is interpreted as a space in query strings. The URL-safe variant, also in RFC 4648, swaps exactly those two:
| Value | Standard | URL-safe |
|---|---|---|
| 62 | + | - |
| 63 | / | _ |
The other 62 characters are identical, and padding is usually dropped since = also needs escaping in URLs. This is the encoding JWTs use for their header and payload segments — which is why a token full of - and _ fails to decode in a tool expecting standard Base64.
Telling them apart
- Contains
+or/→ standard Base64. - Contains
-or_→ base64url. - Ends in
=or==→ padded, so almost certainly standard. - Contains none of those five characters → ambiguous. Both alphabets agree on letters and digits, so a short string can be valid in either.
Converting between them is a plain character substitution plus fixing the padding — no re-encoding required.
Size, and the thing Base64 is not
Four characters for every three bytes means roughly 33% overhead: the encoded form is 4 × ceil(n / 3) characters for n bytes. Worth remembering before inlining a large image as a data URI — a 3 MB photo becomes 4 MB of markup, and unlike a linked file it cannot be cached separately.
And the point that causes real security incidents: Base64 is an encoding, not encryption. It has no key. Anything encoded is trivially readable by anyone who recognises the alphabet. Credentials in a Base64 config value are stored in plain text with an extra step, and a JWT payload is readable by whoever holds the token — signed, not hidden.
Encoding and decoding locally
Because Base64 shows up wherever credentials do — basic auth headers, private keys, API secrets, tokens — an online encoder is an awkward place to paste one. Every string you submit reaches that server's logs.
KeepItLocally's Base64 tool runs entirely in your browser, handles both the standard and URL-safe alphabets, is fully UTF-8 aware, and works on files as well as text. There is no backend to receive anything, and the site's Content-Security-Policy blocks third-party requests — verifiable in DevTools → Network, or by pulling the network cable and watching it keep working.
Quick reference
- A–Z, a–z, 0–9, then
+and/— 64 characters, in that order. =is padding, not a 65th character; only ever one or two, only at the end.- base64url swaps only
+→-and/→_, and usually drops padding. - ≈33% larger than the raw bytes.
- Not encryption — no key, no secrecy.
More background: what Base64 is and when to use it.