What is a ULID?
ULID (Universally Unique Lexicographically Sortable Identifier) is a 128-bit identifier that combines a timestamp with randomness. It is encoded as a 26-character string using Crockford Base32. Unlike UUID v4 which is random and unsortable, ULIDs are always sorted by creation time when you sort them as strings.
ULIDs were created as a modern alternative to UUIDs for cases where time-ordering matters, like database primary keys, event logs, and distributed systems.
How ULIDs Work
A ULID has two parts:
- Timestamp (48 bits, 10 chars): Unix time in milliseconds. This is always the first part, so string sorting equals time sorting.
- Randomness (80 bits, 16 chars): Cryptographically random data for uniqueness within the same millisecond.
The encoding uses Crockford Base32, which excludes the letters I, L, O, and U to avoid visual confusion with digits. This makes ULIDs easy to read, copy, and type.
Monotonic ULIDs
When multiple ULIDs are generated in the same millisecond, the random portion can either be fully random (which doesn't guarantee sort order within that ms) or monotonically incremented.
Monotonic generation takes the previous ULID's random bits and adds 1. This guarantees strict ordering even when generating thousands of IDs per millisecond. Most ULID libraries support this mode.
ULID vs UUID: When to Use Which
- Use ULID when you need sortable IDs, shorter strings, or better database index performance.
- Use UUID v4 when you need maximum compatibility with existing systems that expect UUID format.
- Use UUID v7 as a middle ground: sortable like ULID but in the standard UUID format.
Generate UUIDs with our UUID Generator or decode distributed IDs with the Snowflake ID Decoder.
Crockford Base32 Encoding
ULIDs use Crockford Base32 which encodes 5 bits per character using this alphabet:
0123456789ABCDEFGHJKMNPQRSTVWXYZ
- No I (confused with 1 or l)
- No L (confused with 1 or I)
- No O (confused with 0)
- No U (could be offensive in some combinations)
This results in 26 characters for 128 bits, compared to 36 characters for a UUID. ULIDs are case-insensitive: 01ARZ3NDEK and 01arz3ndek are the same ULID.