UUID Explained: Best Practices for v1, v4, and v7 (2026 Guide)

UUIDs are everywhere in modern software — but choosing the wrong version can tank database performance. Learn what changed between UUIDv1, v4, and v7, when to use each, and why UUIDv7 is the new default for new systems.

UUIDs (Universally Unique Identifiers) are 128-bit identifiers that have become the de facto standard for generating unique IDs in distributed systems. They appear in database rows, session tokens, file names, API request IDs, and a thousand other places.

But here's the catch: not all UUIDs are created equal. The version you choose has huge implications for database performance, index efficiency, and security. UUIDv4 (the random one most people know) is the wrong default for most new systems in 2026 — and UUIDv7 is becoming the modern standard.

What Is a UUID?

A UUID is a 128-bit identifier, conventionally written as 32 hexadecimal characters separated by hyphens in a 8-4-4-4-12 pattern, totaling 36 characters including hyphens. Example:

550e8400-e29b-41d4-a716-446655440000

128 bits means 2¹²⁸ = 340 undecillion possible values. That's enough that generating a billion UUIDs per second, you wouldn't have a collision for ~107 years. Practically unique forever.

UUIDs are defined in RFC 4122 (and updated by RFC 9562 in 2024). They have multiple versions (v1 through v8), each with a different strategy for filling those 128 bits.

The Anatomy of a UUID

A UUID has a specific structure. Let's break it down:

550e8400- e29b -41d4- a716 -446655440000
[time_low]-[time_mid]-[time_hi_version]-[clk_seq_hi_variant]-[node]
  • time_low + time_mid + time_hi together make up the 60-bit timestamp field (in some versions).
  • The version digit (the first digit of the third group: 4 in v4) specifies the version.
  • The variant digit (the first digit of the fourth group: a in standard RFC 4122) specifies the variant (1 = RFC 4122).
  • The node is usually random (v4) or a MAC address (v1).

UUIDv1: Time + MAC Address

UUIDv1 has been around since the original RFC 4122 (2005). It uses:

  • A 60-bit timestamp (100-nanosecond intervals since October 15, 1582)
  • A "clock sequence" to handle sub-second ordering
  • The 48-bit MAC address of the generating machine

This makes UUIDv1 leak information: if you can see multiple v1 UUIDs, you can derive the machine they came from and (roughly) when they were generated. For internal systems this is fine; for anything privacy-sensitive it's not.

More importantly for modern systems: v1 UUIDs sort lexicographically by time, which makes them efficient for database indexes. (This is the one big advantage of v1, and the reason v7 was created to give you the same property without the privacy leak.)

UUIDv4: Pure Random

UUIDv4 uses 122 bits of random data and 6 reserved bits (4 for version, 2 for variant). This is what most people think of as "a UUID" — they look like:

f47ac10b-58cc-4372-a567-0e02b2c3d479

The randomness makes v4 UUIDs extremely unlikely to collide (1 in 2¹²², even with billions per second). They also leak no information about when or where they were generated — which is great for privacy but bad for performance.

The big problem: Because v4 UUIDs are random, they don't sort by creation time. If you make v4 UUID your database primary key, every insert causes random page splits in B-tree indexes. On large tables, this kills write throughput and bloats index size. A common mistake is to make v4 UUIDs the primary key of a high-write MySQL table — and then wonder why it slows to a crawl after 10 million rows.

UUIDv7: Time-Ordered Random (The New Default)

UUIDv7 was introduced in RFC 9562 (May 2024, replacing the draft RFC). It solves v4's database problem while keeping v4's privacy properties:

  • First 48 bits: Unix timestamp in milliseconds
  • Next 4 bits: Version (7)
  • Next 12 bits: Random (for sub-millisecond collisions)
  • Last 64 bits: Random (cryptographically secure)

Result: UUIDv7 sorts by time (so it's a great database primary key) without leaking the machine's MAC address (so it's privacy-preserving). It's the default choice for new systems in 2026.

UUIDv5: Deterministic from a Namespace

UUIDv5 is generated by hashing (SHA-1) a namespace UUID plus a name. Given the same inputs, you always get the same UUID. This is useful for:

  • Generating the same UUID for the same file content (content-addressable IDs)
  • Generating UUIDs without a CSPRNG (deterministic systems)
  • Cross-system identifiers where two systems need to agree on IDs without coordination

UUIDv8: Custom (For Application-Specific Layouts)

UUIDv8 is for custom UUID layouts. If v7 doesn't fit your needs (e.g., you need a custom time format or a specific entropy distribution), v8 lets you define your own structure. Most projects won't need this.

v6: Re-ordered Time (Less Common)

UUIDv6 reorders v1's timestamp fields for better sort order, but its use is rare. UUIDv7 superseded it for most purposes.

Which UUID Version Should You Use in 2026?

Use case Recommended version Why
Database primary keysv7Time-sorted, no MAC leak, fast B-tree writes
API request/transaction IDsv4 or v7Pure random is fine here, v7 if you want time-ordering
Session tokensv4Avoid leaking creation time to clients
Content-addressable IDsv5Same input → same UUID, no randomness needed
Distributed identifiers where you don't control the generatorv4Universal compatibility, no assumptions
Filename or pathv4 or v7Either works; v7 benefits from time ordering

UUIDs and Database Performance (Why v7 Matters)

The biggest real-world UUID mistake is using v4 as a primary key in a high-write database. Here's why:

Most databases (Postgres, MySQL InnoDB, MongoDB WiredTiger) use B-tree indexes. With an integer primary key that's auto-incremented, new rows are always appended at the end — sequential writes, fast and cache-friendly.

With a random UUIDv4 primary key, new rows land at random positions in the index. Every insert causes a random page read (to find the right leaf) plus a page split if the leaf is full. On a busy table with millions of rows, this converts the fast sequential append into a slow random-access write pattern. Insert throughput can drop 5-10x.

UUIDv7 fixes this by including a sortable timestamp prefix. New UUIDs are roughly monotonically increasing (with sub-millisecond randomness), so inserts stay cache-friendly. You get the distributed-uniqueness of UUIDs without the random-write penalty.

UUID Collisions: When To Worry (And When Not To)

The math on random UUID collisions uses the birthday problem. For 128-bit UUIDs, you can generate 2.3 billion UUIDs per second for 100 years and have only a 50% chance of one collision. That's effectively impossible.

Even the vastly more constrained UUIDv1 (60-bit timestamp + 14-bit clock sequence) only collides if you generate more than 16,384 per millisecond on the same machine. That's why v7 includes extra random bits for sub-millisecond uniqueness.

Bottom line: don't worry about collisions unless you're doing something unusual like regenerating UUIDs every microsecond across a million machines. The randomness is enough.

UUID vs ULID (When to Pick Which)

ULIDs (Universally Unique Lexicographically Sortable Identifier) have similar properties to UUIDv7 (26-character Base32, time-sorted, random). The main differences:

  • ULID: 26 characters, Crockford Base32 (no I, L, O, U), case-insensitive
  • UUIDv7: 36 characters with hyphens, RFC 9562 compliant

If you're starting fresh in 2026, UUIDv7 is the safer pick — it's an RFC standard, integrates with every UUID-aware library, and has wide database support. ULID is fine but is an additional concept your team needs to learn.

Common UUID Gotchas

Gotcha 1: Storing UUIDs as Strings

Most databases can store UUIDs efficiently as a 16-byte binary type (PostgreSQL uuid, MySQL BINARY(16)). Storing them as 36-character strings doubles the storage cost and breaks sorting. Always use the native UUID column type.

Gotcha 2: URL-Encoding Issues

Standard hex UUIDs are URL-safe (0-9, a-f, hyphens). But if you ever URL-encode one for safety, do it consistently. Some libraries add hyphens; some don't. Mismatches cause "UUID not found" debugging nightmares.

Gotcha 3: Mixed v4 and v7 in One Table

If some rows have v4 UUIDs (random) and others have v7 UUIDs (time-sorted), your index locality breaks. Stick to one version per table — usually v7.

Gotcha 4: Using UUID as a Password

UUIDs are identifiers, not secrets. v1 leaks the machine ID; v4 leaks nothing but is publicly visible if logged. Never use a UUID as a session token without signing it (see JWTs) or encrypting it.

Try It Yourself

Need UUIDs for your next project? Use our free UUID Generator — supports v1, v4, and v7, with bulk generation for seeding test databases. Generate 100,000 v7 UUIDs in a second and see the time-sortable pattern firsthand.

Generating UUIDs for documentation examples? Try our bulk UUID generator — export to CSV or JSON, ready to paste into your schema.

Working on a high-write database? Pair UUIDv7 with proper index design (the Base64 guide's discussion of consistent encoding applies to UUIDs too — pick one format per system, stick with it).

About LaiUse

LaiUse is a free browser-based productivity platform with 178 tools across 12 categories. Every tool runs in your browser — your files never leave your device. Read more on our about page, or browse all free tools.