What is Base64 Decoding?
Base64 encoding turns arbitrary binary data (bytes) into a string of 64 printable ASCII characters — A-Z, a-z, 0-9, +, and /. Decoding reverses that: given a Base64 string, you recover the original bytes. Those bytes might be UTF-8 text, JSON, a JWT header/payload, an image, a PDF, or any other binary blob.
Base64 is used everywhere: HTTP Basic Authentication headers, JWT tokens, data URLs in CSS/HTML, MIME email attachments, SSH keys, TLS certificates, and countless serialization protocols. Whenever you need to move binary data through a text-only channel, Base64 is the go-to encoding.
Why Use an Online Base64 Decoder Instead of the Command Line?
You could just run echo "SGVsbG8=" | base64 -d in your terminal — and that works fine for small ASCII strings. But there are real cases where a browser tool wins:
- Long strings — pasting a 2000-character JWT into a terminal is painful. In a browser, ctrl+V just works.
- UTF-8 gotchas — the CLI
base64command decodes to raw bytes and dumps them to stdout. Non-ASCII characters appear mangled. Our tool usesTextDecoderto render UTF-8 correctly. - URL-safe variants — the CLI doesn't handle
-/_substitutions. You'd have totrthem back to+//first. - Missing padding — JWT payloads have padding stripped. CLI
base64 -derrors out; our tool auto-adds the padding. - Privacy — same as CLI, nothing leaves your machine. Better than pasting a token into a random third-party server.
How Base64 Decoding Works Under the Hood
Base64 groups 3 bytes of input into 4 output characters. Each output character represents 6 bits (26 = 64 possible values, hence the name). To decode:
- Look up each character in the Base64 alphabet to get a 6-bit value.
- Concatenate the 6-bit chunks back into a bit stream.
- Split the bit stream into 8-bit bytes.
- The
=padding characters are dropped — they only exist to mark how much of the last group is real.
Example: SGVsbG8= → 4 chars = 24 bits = 3 bytes = 0x48 0x65 0x6c plus the last group of one character which represents 1 byte = 0x6f. Reassembled:0x48 0x65 0x6c 0x6c 0x6f= "Hello".
Decoding UTF-8 Text Correctly
The single most common Base64 decoding bug is UTF-8 mangling. Here is what happens and how to fix it:
// Encoded: 'Hello 世界 👋' as UTF-8, then Base64
const encoded = 'SGVsbG8g5LiW55WMIPCfkYs=';
// WRONG — atob() returns a "binary string" of raw byte codes
atob(encoded);
// → "Hello ä¸ç ð" (garbled!)
// CORRECT — decode the bytes as UTF-8
new TextDecoder().decode(
Uint8Array.from(atob(encoded), c => c.charCodeAt(0))
);
// → "Hello 世界 👋" (correct)Handling URL-Safe Base64 and Missing Padding
function base64UrlDecode(str) {
// 1. Restore standard Base64 alphabet
let b64 = str.replace(/-/g, '+').replace(/_/g, '/');
// 2. Restore padding
const pad = b64.length % 4;
if (pad) b64 += '='.repeat(4 - pad);
// 3. Decode + UTF-8 render
return new TextDecoder().decode(
Uint8Array.from(atob(b64), c => c.charCodeAt(0))
);
}
// Works for JWT payloads
const jwt = 'eyJ1c2VyIjoi5LiW55WMIn0'; // no padding
console.log(base64UrlDecode(jwt)); // → {"user":"世界"}Decoding a Base64 Image
// Common case: a data URL like "data:image/png;base64,iVBORw0KG..."
function decodeBase64Image(dataUrl) {
const [prefix, b64] = dataUrl.split(',');
const mimeMatch = prefix.match(/data:([^;]+);base64/);
const mime = mimeMatch ? mimeMatch[1] : 'application/octet-stream';
const bytes = Uint8Array.from(atob(b64), c => c.charCodeAt(0));
const blob = new Blob([bytes], { type: mime });
return URL.createObjectURL(blob);
}
// Use it
const imgSrc = decodeBase64Image(myDataUrl);
document.getElementById('preview').src = imgSrc;Common Decoding Errors
- InvalidCharacterError: Failed to execute 'atob' — the input contains characters outside the Base64 alphabet (whitespace, quotes, non-ASCII). Strip whitespace with
str.replace(/\s+/g, '')before decoding. - Output is garbled UTF-8 — you used
atob()directly. Wrap it inTextDecoderas shown above. - Length is not a multiple of 4 — padding is missing. Add it manually:
str + '='.repeat((4 - str.length % 4) % 4). - Result looks like binary garbage — the source was probably a file (image, PDF, etc.), not text. Treat the output as bytes, not a string.
- Silent truncation — some copy-paste operations drop trailing
=characters. Verify your input string length before decoding.
Key Facts
- Native function:
- window.atob() in every browser since IE10
- Output type:
- Binary string (one char = one byte) — needs TextDecoder for UTF-8
- Size ratio:
- Base64 → bytes is 4:3 (decoded is ~75% of encoded)
- Character set:
- A-Z, a-z, 0-9, +, /, = padding (URL-safe uses - and _)
- Common uses:
- JWT payloads, data URLs, HTTP Basic Auth, MIME attachments
- Server round-trip:
- None — all decoding happens in your browser
Related Base64 Tools
- Decode Base64 String — string-focused decoder walkthrough
- Base64 Decode JavaScript — atob() and TextDecoder patterns
- Base64 Decode Python — base64.b64decode() guide
- Base64 Image Decoder — decode data URLs to viewable images
- Base64 Encode Online — reverse direction
- JWT Debugger — decode entire JWT tokens