Skip to content
100% in your browser. Nothing you paste is uploaded — all processing runs locally. Read more →

UUID vs Nanoid

On this page
  1. At a glance
  2. Why nanoid is shorter
  3. Length vs. recognizability
  4. Where nanoid wins
  5. Where UUID wins
  6. Pattern: UUID internal, nanoid public
  7. Code
    1. Nanoid
    2. UUID
  8. Collision math for short nanoids
  9. Don’t try this
  10. Decision matrix
  11. Try the tools

Nanoid is a small library that generates short, URL-friendly, random IDs. It’s not a UUID — it’s a different design with different trade-offs.

TL;DR. Use a UUID for anything that needs the universal standard (database keys, cross-system IDs, anything you’ll regret if it conflicts with another system). Use nanoid for public-facing short IDs where you control the alphabet and want pretty URLs (e.g. shortener slugs, share links, public IDs that hide the database key).

At a glance

UUID v4Nanoid (default)
Length36 chars (with hyphens)21 chars
Bits122 random126 random
Alphabet16 (hex)64 (URL-safe)
Formatxxxxxxxx-xxxx-Mxxx-Nxxx-xxxxxxxxxxxxV1StGXR8_Z5jdHi6B-myT
StandardRFC 4122 / 9562npm package, ad-hoc
Database native typeyesno (stored as text)
Time-ordered versionyes (v7)no
Customizable alphabetnoyes

Why nanoid is shorter

UUID uses base 16 (hex) and adds hyphens. Nanoid uses base 64 (URL-safe alphanumerics + _ and -). With more characters per byte of information, you get a shorter string for the same randomness budget.

122 bits in base 16: ⌈122/4⌉ = 31 hex chars (UUID adds 4 hyphens → 35 visible)
126 bits in base 64: ⌈126/6⌉ = 21 chars

Nanoid actually has more random bits (126 vs 122) in fewer characters, because UUID burns 6 bits on the version + variant metadata.

Length vs. recognizability

LengthExampleTrade-off
36 (UUID)0e6f1b8c-2c33-4f1f-9c0b-2a3d4e5f6a7bUniversally recognized as an ID
21 (nanoid)V1StGXR8_Z5jdHi6B-myTLooks like random gibberish to a reader
8 (custom nanoid)aB3cD4eFPretty URL — but 48 bits, collision risk
4 (custom nanoid)aB3cURL slug territory — must check for collisions

UUIDs in URLs scream “this is an internal ID.” Short nanoids look like part of the brand. Use this distinction.

Where nanoid wins

Where UUID wins

Pattern: UUID internal, nanoid public

The cleanest design uses both:

users
├── id          uuid     primary key (v7)
├── public_id   text     nanoid for URLs ("V1StGXR8")
└── ...

Code

Nanoid

import { nanoid, customAlphabet } from "nanoid";

nanoid();           // "V1StGXR8_Z5jdHi6B-myT"  — 21 chars
nanoid(8);          // "aB3cD4eF"               — 8 chars
nanoid(8, /* not the third arg, this is wrong */);

// Custom alphabet (no confusing 0/O/1/l/I)
const code = customAlphabet("23456789ABCDEFGHJKLMNPQRSTUVWXYZ", 6);
code();             // "X4M2KP"

UUID

import { v4, v7 } from "uuid";

v4();               // "0e6f1b8c-2c33-4f1f-9c0b-2a3d4e5f6a7b"
v7();               // "01928a47-3b30-7c5e-9d1a-f0b8c4a7e923"

Collision math for short nanoids

The whole point of UUID’s 122 random bits is “you’ll never collide.” Nanoid lets you go shorter, which means you have to check.

For a nanoid of length L over alphabet size A, the birthday-paradox 1% threshold (~1% chance of any collision) is:

LAlphabet1% threshold
8 chars64~21,000 IDs
10 chars64~1.3 million IDs
12 chars64~85 million IDs
14 chars64~5.5 billion IDs
21 chars (default)64~10²⁰ IDs (effectively zero)

If you go below the default 21, add a unique constraint to your database column and retry on collision. The retry rate is tiny but non-zero.

Don’t try this

Decision matrix

What's the ID for?
├── DB primary key                    → UUID (v7 if greenfield, v4 if not)
├── Public URL slug                   → nanoid (custom length, no confusing chars)
├── Share / invite token              → nanoid
├── API key                           → 32+ char nanoid OR signed JWT (not raw UUID)
├── Cross-service correlation         → UUID (logs, traces — std format wins)
├── Cookie / session                  → signed token, not a raw ID of either kind
└── Generic identifier with no specific need → UUID (boring is good)

Try the tools