Tabla de prefijos
Cada fila se comprobó codificando los bytes mágicos reales del formato. El «prefijo estable» es la parte que nunca cambia en ese formato. Los caracteres que siguen dependen del resto del archivo.
| Prefijo Base64 | Bytes mágicos (hex) | Formato | Ábrelo con |
|---|---|---|---|
iVBORw0KGgo | 89 50 4E 47 0D 0A 1A 0A | PNG | Base64 a PNG |
/9j/ | FF D8 FF | JPEG | Base64 a JPG |
R0lGOD | 47 49 46 38 (GIF8) | GIF (R0lGODlh = GIF89a, R0lGODdh = GIF87a) | Base64 a GIF |
UklGR | 52 49 46 46 (RIFF) | WebP, WAV, AVI | Base64 a WebP, Base64 a WAV |
JVBERi0 | 25 50 44 46 2D (%PDF-) | Base64 a PDF | |
UEsDB | 50 4B 03 04 (PK..) | ZIP, DOCX, XLSX, PPTX, JAR, APK, EPUB | Base64 a ZIP, Word, Excel |
H4sI | 1F 8B 08 | gzip | Decodificar Base64 gzip |
eJ, eN, eF, eA | 78 9C, 78 DA, 78 5E, 78 01 | zlib | Zlib y Base64 |
eyJ | 7B 22 ({") | Objeto JSON, JWT | Base64 a JSON, decodificador JWT |
PD94bWwg | 3C 3F 78 6D 6C 20 (<?xml ) | XML, SVG con declaración | Base64 a XML |
PHN2Zy | 3C 73 76 67 20 (<svg ) | SVG sin declaración (<svg más un salto de línea da PHN2Zw) | Base64 a SVG |
MII | 30 82 | DER: certificados, claves, CSR | decodificador de certificados |
AAAA | 00 00 00 | Blob de clave pública SSH, o ceros iniciales | huella de clave SSH |
SUQz | 49 44 33 (ID3) | MP3 con etiqueta ID3v2 | Base64 a MP3 |
AAABAA | 00 00 01 00 | ICO | Base64 a ICO |
d09GMg | 77 4F 46 32 00 (wOF2) | Fuente WOFF2 con contornos TrueType (las fuentes CFF empiezan por d09GMk9UVE8) | Base64 a fuente |
TVqQ | 4D 5A 90 (MZ) | EXE o DLL de Windows (algunos enlazadores escriben MZP, que da TVpQ) | Base64 a archivo |
f0VMR | 7F 45 4C 46 (.ELF) | Binario ELF de Linux | Base64 a archivo |
Algunas filas merecen un comentario:
- RIFF es un contenedor. El nombre del formato está en los bytes 8 a 11, y los bytes 9 a 11 se codifican como los caracteres 13.º a 16.º:
RUJQpara WebP (EBP),QVZFpara WAV (AVE),Vkkgpara AVI (VI). La primera letra del nombre del formato comparte grupo de 3 bytes con el tamaño del archivo, así que no produce un carácter estable. - zlib no tiene un único prefijo. El segundo byte indica el nivel de compresión:
eJpara el nivel por defecto,eNpara los niveles 7 a 9,eFpara 2 a 5,eApara 0 y 1 (tal como los escribezlibde Python). - JSON empieza por
eyJsolo cuando los dos primeros caracteres son{"sin espacio.{ "a": 1 }empieza poreyAi, un{formateado con salto de línea empieza porewoy un array[empieza porW. - DER: las estructuras empiezan con una etiqueta SEQUENCE
30, que siempre daM. Una longitud de dos bytes (30 82) daMII, y el siguiente carácter depende de la longitud: una clave pública RSA 2048 esMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA, y un certificado típico esMIIC,MIIDoMIIE. Las estructuras cortas usan una longitud de un byte: una clave privada Ed25519 empieza porMC4Cy una clave pública P-256 porMFkw. - Claves públicas SSH: empiezan con una longitud big-endian de 4 bytes, así que el blob empieza por
AAAA. Los caracteres siguientes deletrean el tipo de clave:AAAAC3NzaC1lZDI1NTE5esssh-ed25519,AAAAB3NzaC1yc2Eesssh-rsa,AAAAE2VjZHNhesecdsa. Fuera de SSH, una serie deAsignifica bytes cero. - MP3: los archivos sin etiqueta ID3 empiezan directamente con una cabecera de trama. Sus bits de sincronización
FF Fxdan un//inicial, por ejemplo//uQparaFF FB 90. - Base64URL sustituye
+y/, así que el prefijo de JPEG pasa a ser_9j_. Los demás prefijos de la tabla no contienen ninguno de los dos caracteres y se ven igual en ambos alfabetos.
Por qué el prefijo es estable
Base64 trabaja con grupos de 3 bytes. Cada grupo de 3 bytes se convierte exactamente en 4 caracteres, y esos 4 caracteres dependen solo de esos 3 bytes. Nada de lo que viene después en el archivo influye hacia atrás. Así que si un formato siempre empieza con los mismos 3 bytes, su Base64 siempre empieza con los mismos 4 caracteres.
bytes: FF D8 FF
bits: 11111111 11011000 11111111
groups: 111111 111101 100011 111111
index: 63 61 35 63
chars: / 9 j /
Cuando la parte mágica fija no mide un múltiplo de 3 bytes, el último grupo mezcla bits conocidos con bits del resto del archivo. Toma los 5 bytes de %PDF-. Los 3 primeros bytes dan 4 caracteres estables (JVBE). Los 2 siguientes dan 2 más (Ri), y el séptimo carácter mezcla los últimos 4 bits de - con los 2 primeros bits del dígito de versión. Todos los dígitos empiezan por los bits 00, así que en la práctica ese carácter siempre es 0. Después de JVBERi0 asoma la versión: JVBERi0xLjQ es %PDF-1.4, JVBERi0xLjc es %PDF-1.7, JVBERi0yLjA es %PDF-2.0.
La firma PNG tiene 8 bytes, lo que da 10 caracteres estables. El undécimo mezcla el último byte de la firma con el primer byte de la longitud del bloque IHDR, que siempre es 0, así que iVBORw0KGgo se mantiene. Como todo PNG continúa con ese bloque IHDR, los PNG reales comparten un prefijo aún más largo: iVBORw0KGgoAAAANSUhEUg.
Cuándo se desplaza el prefijo
El prefijo solo funciona cuando los bytes mágicos están en la posición 0, 3, 6, etc. Añade un byte delante y todos los grupos se desplazan, así que los caracteres cambian por completo:
| Entrada | El Base64 empieza por |
|---|---|
| Firma PNG | iVBORw0KGgoAAAA |
| 1 byte + firma PNG | AIlQTkcNChoKAAAA |
| 2 bytes + firma PNG | AACJUE5HDQoaCgAA |
| 3 bytes + firma PNG | AAAAiVBORw0KGgoA |
Con 3 bytes extra se recupera la alineación y el prefijo conocido reaparece 4 caracteres después. Motivos habituales de un prefijo desplazado o ausente:
- Una marca de orden de bytes (BOM). El texto UTF-8 con BOM empieza por
77u/(EF BB BF). La BOM mide 3 bytes, así que un JSON detrás sigue mostrandoeyJ:77u/eyJ…. El texto UTF-16 con BOM empieza por//4o//5(little-endian) o por/v8(big-endian). - Texto UTF-16. El texto guardado como UTF-16LE pone un byte cero detrás de cada carácter ASCII, lo que produce muchas
A:Hellose convierte enSABlAGwAbABvAA==. El-EncodedCommandde PowerShell tiene este aspecto. Usa el decodificador de PowerShell o Base64 a UTF-16. - Compresión o cifrado. Un PNG comprimido con gzip empieza por
H4sI, y un archivo cifrado no tiene ningún prefijo reconocible. - Una data URI.
data:image/png;base64,es una cabecera; el Base64 empieza después de la coma. El analizador de data URI las separa por ti. - Saltos de línea y espacios. No desplazan los bytes, pero una búsqueda del prefijo con
startswithfallará si la cadena empieza por un salto de línea o unas comillas. Recorta antes, o pásala por Reparar Base64.
Comprobar un prefijo en código
Puedes comparar los primeros caracteres como cadenas, pero comparar los bytes decodificados da menos errores: los números mágicos salen directamente de la especificación de cada formato y nunca tienes que averiguar qué caracteres son estables. Decodificar solo los 12 primeros caracteres da los 9 primeros bytes, suficiente para la mayoría de las firmas:
import base64
SIGNATURES = {
b"\x89PNG\r\n\x1a\n": "png",
b"\xff\xd8\xff": "jpeg",
b"%PDF-": "pdf",
b"PK\x03\x04": "zip",
b"\x1f\x8b": "gzip",
}
def sniff(b64: str) -> str:
head = base64.b64decode(b64.strip()[:12])
for magic, name in SIGNATURES.items():
if head.startswith(magic):
return name
return "unknown"
print(sniff("iVBORw0KGgoAAAANSUhEUgAAAAEAAAAB")) # png
print(sniff("JVBERi0xLjcKJcfsj6IK")) # pdf
La herramienta Base64 a archivo hace la misma comprobación con una lista más larga y muestra una vista previa cuando el navegador puede representar el formato. Para ver cómo se asignan los grupos de 6 bits a caracteres, consulta cómo funciona Base64 y la tabla del alfabeto.
Preguntas frecuentes
¿Qué significa una cadena Base64 que empieza por iVBORw0KGgo?
Es una imagen PNG. iVBORw0KGgo es la forma Base64 de la firma PNG de 8 bytes 89 50 4E 47 0D 0A 1A 0A. Pégala en Base64 a PNG para verla.
¿Qué es /9j/ al principio de una cadena Base64?
Un JPEG. Los bytes FF D8 FF con los que empieza todo archivo JPEG se codifican como /9j/. En Base64URL el mismo prefijo se escribe _9j_.
¿Por qué los JWT siempre empiezan por eyJ?
La cabecera de un JWT es un objeto JSON, así que empieza por {", y esos dos bytes se codifican como eyJ. La parte de la carga útil empieza por eyJ por la misma razón.
Mi Base64 no coincide con ningún prefijo conocido. ¿Y ahora qué?
Puede que los datos tengan bytes de más delante, estén comprimidos o cifrados, o sean texto normal. La herramienta Base64 a archivo decodifica los datos y compara los bytes con muchas firmas.