Generador NanoID
Genera IDs únicos pequeños y seguros para URL con alfabeto personalizable
Alfabeto
Tamaño
Cantidad
Haz clic en Generar para crear NanoIDs
¿Qué es NanoID?
NanoID es un generador de IDs aleatorios pequeño, rápido y seguro para URL. Por defecto produce cadenas de 21 caracteres usando un alfabeto de 64 caracteres (A-Za-z0-9_-), proporcionando aproximadamente 126 bits de entropía — comparable a los 122 bits de UUID v4 pero en una cadena más corta.
NanoID no incorpora una marca de tiempo ni ningún dato estructurado. Cada ID es puramente aleatorio, generado a partir del generador de números aleatorios criptográficamente seguro del sistema operativo (crypto.getRandomValues() en navegadores, crypto.randomBytes() en Node.js).
NanoID vs UUID v4
NanoID y UUID v4 son ambos generadores de IDs aleatorios respaldados por un CSPRNG. Difieren en formato, longitud y soporte del ecosistema:
| Propiedad | NanoID (predeterminado) | UUID v4 |
|---|---|---|
| Formato | Alfanumérico seguro para URL + _- | Hexadecimal con guiones |
| Longitud | 21 caracteres (predeterminado) | 36 caracteres |
| Entropía | ~126 bits | 122 bits |
| Seguro para URL | Sí — sin codificación necesaria | Sí (con guiones) |
| Alfabeto | 64 caracteres (A-Za-z0-9_-) | 16 caracteres (0-9a-f) |
| Dependencias | Requiere paquete npm | Nativo (crypto.randomUUID) |
| Personalizable | Sí — longitud y alfabeto | No |
| Estándar | Ninguno (biblioteca comunitaria) | RFC 4122 / RFC 9562 |
Elija UUID v4 cuando la interoperabilidad con sistemas externos importa — bases de datos con columnas UUID nativas, APIs que esperan formato UUID, o infraestructura de registro que analiza UUIDs. Elija NanoID cuando quiera IDs más cortos y controle la pila completa.
Probabilidad de Colisión por Tamaño
La probabilidad de colisión de NanoID depende de la longitud del ID y la tasa de generación. La siguiente tabla usa el alfabeto de 64 caracteres predeterminado:
| Tamaño (caracteres) | IDs posibles | Seguridad de colisión |
|---|---|---|
| 6 | 64 | ~1 en 4.500M — seguro para unos pocos miles de IDs |
| 8 | 64 | ~1 en 4,5 billones — seguro para millones de IDs |
| 11 | 64 | ~1 en 2,8 cuatrillones — seguro para miles de millones de IDs |
| 16 | 64 | ~1 en 1,2 × 10^19 — seguro para billones de IDs |
| 21 | 64 | ~1 en 10^30 — seguro para 100 mil millones de IDs por día durante siglos |
| 32 | 64 | Comparable a UUID v4 (122 bits) |
| 36 | 36 | Supera a UUID v4 |
El tamaño predeterminado de 21 caracteres se elige para coincidir con la resistencia a colisiones de UUID v4 (~126 bits) siendo un 41% más corto. Para la mayoría de las aplicaciones, 21 caracteres es la elección correcta.
Alfabetos Personalizados
El alfabeto de NanoID es completamente personalizable. La biblioteca acepta cualquier cadena de caracteres únicos como alfabeto y genera IDs usando solo esos caracteres:
A-Za-z0-9_-A-Za-z0-90-9a-f0-9Importante: use nanoid/non-secure solo para aplicaciones no sensibles a la seguridad (p. ej. IDs de elementos UI). Para cualquier ID que deba ser imposible de adivinar, siempre use la importación segura predeterminada.
Cómo NanoID Genera Aleatoriedad
NanoID usa el generador de números pseudoaleatorios criptográficamente seguro (CSPRNG) del sistema operativo. En navegadores es crypto.getRandomValues(); en Node.js es crypto.randomFillSync(). Esta es la misma fuente de entropía usada para las claves de sesión TLS — mucho más fuerte que Math.random().
Muestreo por Rechazo (Evitando el Sesgo de Módulo)
Un enfoque ingenuo para generar caracteres aleatorios sería: tomar un byte aleatorio (0–255) y calcular byte % alphabetSize. Esto introduce el sesgo de módulo — algunos caracteres aparecen ligeramente más a menudo que otros cuando el tamaño del alfabeto no divide uniformemente 256.
NanoID elimina este sesgo usando el muestreo por rechazo:
- Determine la máscara de potencia de dos más pequeña que cubra el tamaño del alfabeto (p. ej. para un alfabeto de 64 caracteres, la máscara es 63 = 0b00111111)
- Genere bytes aleatorios y aplique la máscara:
byte & mask - Si el valor enmascarado está dentro del rango del alfabeto, úselo. De lo contrario, descarte e intente de nuevo.
Esto significa que algunos bytes aleatorios son descartados, pero el resultado es una distribución perfectamente uniforme sobre el alfabeto — ningún carácter es más probable que otro.
// Pure browser — no npm package needed
function generateNanoid(alphabet, size) {
const mask = (2 << (31 - Math.clz32((alphabet.length - 1) | 1))) - 1
const step = Math.ceil((1.6 * mask * size) / alphabet.length)
let id = ''
while (id.length < size) {
const bytes = crypto.getRandomValues(new Uint8Array(step))
for (const byte of bytes) {
const idx = byte & mask
if (idx < alphabet.length) {
id += alphabet[idx]
if (id.length === size) break
}
}
}
return id
}
const URL_SAFE = 'useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict'
generateNanoid(URL_SAFE, 21) // → "V1StGXR8_Z5jdHi6B-myT"Soporte de Entorno
Ejemplos de Código
JavaScript / TypeScript
// npm i nanoid
import { nanoid } from 'nanoid'
nanoid() // → "V1StGXR8_Z5jdHi6B-myT" (21 chars, URL-safe)
nanoid(8) // → "Uakgb_J5" (custom size)
// Custom alphabet
import { customAlphabet } from 'nanoid'
const hexId = customAlphabet('0123456789abcdef', 16)
hexId() // → "4f3a1b8c9d2e0f7a"
const numId = customAlphabet('0123456789', 8)
numId() // → "30812894"Navegador (CDN)
NanoID puede usarse directamente en el navegador mediante una importación CDN. No se requiere paso de compilación para prototipado rápido.
// Pure browser — no npm package needed
function generateNanoid(alphabet, size) {
const mask = (2 << (31 - Math.clz32((alphabet.length - 1) | 1))) - 1
const step = Math.ceil((1.6 * mask * size) / alphabet.length)
let id = ''
while (id.length < size) {
const bytes = crypto.getRandomValues(new Uint8Array(step))
for (const byte of bytes) {
const idx = byte & mask
if (idx < alphabet.length) {
id += alphabet[idx]
if (id.length === size) break
}
}
}
return id
}
const URL_SAFE = 'useandom-26T198340PX75pxJACKVERYMINDBUSHWOLF_GQZbfghjklqvwyzrict'
generateNanoid(URL_SAFE, 21) // → "V1StGXR8_Z5jdHi6B-myT"Python
# pip install nanoid
from nanoid import generate
generate() # → "V1StGXR8_Z5jdHi6B-myT"
generate(size=8) # → "Uakgb_J5"
generate('0123456789abcdef', 16) # custom alphabet + sizeNode.js (CommonJS)
// Node.js — stdlib only, no npm needed
const { randomFillSync } = require('crypto')
function nanoid(alphabet, size) {
const mask = (2 << (31 - Math.clz32((alphabet.length - 1) | 1))) - 1
const step = Math.ceil((1.6 * mask * size) / alphabet.length)
let id = ''
while (id.length < size) {
const bytes = randomFillSync(Buffer.alloc(step))
for (const byte of bytes) {
const idx = byte & mask
if (idx < alphabet.length) { id += alphabet[idx]; if (id.length === size) break }
}
}
return id
}