Introduction
idt (ID Tool) is a fast, ergonomic CLI tool for working with various identifier formats. Whether you need to generate, inspect, convert, or validate IDs, idt provides a unified interface for all your identifier needs.
Key Features
- Multi-format Support: Work with UUID (all versions), ULID, NanoID, Snowflake, assigned IDs (EAN, ISBN, ISIN), and more
- Generate IDs: Create new identifiers with customizable options
- Inspect IDs: Decode and analyze any supported ID format
- Convert Formats: Transform IDs between different encodings (hex, base64, base58, etc.)
- Validate IDs: Check if strings are valid identifiers
- Compare IDs: Analyze relationships between IDs (chronological, binary, lexicographic)
- Pipe-friendly: Designed for shell scripting and Unix pipelines
- JSON Output: Machine-readable output for integration with other tools
Quick Example
# Generate a UUIDv7 (time-sortable)
$ idt gen uuidv7
019c04e5-6118-7b22-95cb-a10e84dad469
# Inspect the generated ID
$ idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469
UUIDV7
019c04e5-6118-7b22-95cb-a10e84dad469
Time (UTC) 2026-01-28T13:57:47.416Z
Local Time (+09:00) 2026-01-28T22:57:47.416+09:00
Version 7
Variant RFC4122
Random 62 bits
Hex 019c04e561187b2295cba10e84dad469
Base64 AZwE5WEYeyKVy6EOhNrUaQ==
Int 2139325608653621017571381452845274217
# Convert to different formats
$ idt convert 019c04e5-6118-7b22-95cb-a10e84dad469 -f base64
AZwE5WEYeyKVy6EOhNrUaQ==
Why idt?
Working with different ID formats often requires multiple tools or libraries. idt consolidates these into a single, fast CLI tool that:
- Auto-detects ID types - No need to specify the format when inspecting or converting
- Provides rich metadata - Extract timestamps, version info, and other embedded data
- Supports modern formats - UUIDv7, ULID, and other time-sortable IDs
- Integrates with your workflow - JSON output, stdin support, and Unix-friendly design
Supported ID Types
| Type | Sortable | Timestamp | Bits | Description |
|---|---|---|---|---|
| UUIDv1 | No | Yes | 128 | Timestamp + MAC address |
| UUIDv4 | No | No | 128 | Random |
| UUIDv6 | Yes | Yes | 128 | Reordered timestamp |
| UUIDv7 | Yes | Yes | 128 | Unix timestamp + random |
| ULID | Yes | Yes | 128 | Crockford Base32, lexicographically sortable |
| NanoID | No | No | ~126 | Compact URL-friendly ID |
| Snowflake | Yes | Yes | 64 | Twitter/Discord-style distributed ID |
| EAN-13 | - | - | - | International retail barcode (validate only) |
| ISBN-13 | - | - | - | Book identifier (validate only) |
| ISBN-10 | - | - | - | Legacy book identifier (validate only) |
| ISIN | - | - | - | Securities identifier (validate only) |
| EAN-8 | - | - | - | Small item barcode (validate only) |
| UPC-A | - | - | - | Product code (validate only) |
| ISSN | - | - | - | Serial number (validate only) |
| ISMN | - | - | - | Music number (validate only) |
| ISNI | - | - | - | Name identifier (validate only) |
| GTIN-14 | - | - | - | Trade item number (validate only) |
| ASIN | - | - | - | Amazon identifier (validate only) |
See the ID Types Overview for complete details on all supported formats.
Getting Started
Ready to start using idt? Head to the Installation guide to get set up, then check out the Quick Start for common usage patterns.
Installation
Using Cargo
# Install from crates.io
cargo install idt
# Install from git repository
cargo install --git https://github.com/sh-cho/idt
Build from Source
Clone the repository and build:
git clone https://github.com/sh-cho/idt.git
cd idt
cargo install --path .
Using Homebrew
brew install sh-cho/tap/idt
# or
brew tap sh-cho/tap
brew install idt
Using Nix (flakes)
# Try without installing
nix run github:sh-cho/idt -- --help
# Install persistently
nix profile install github:sh-cho/idt
Using Docker
# From Docker hub
docker run --rm seonghyeon/idt:{version} --help
# From GitHub Container Registry
docker run --rm ghcr.io/sh-cho/idt:{version} --help
Docker image is published to the registries below:
Next Steps
Now that you have idt installed, head to the Quick Start guide to learn the basics.
Quick Start
This guide covers the essential idt commands to get you productive quickly.
Generating IDs
Generate IDs with the gen command:
# Generate a random UUID (v4)
idt gen uuid
# Generate a time-sortable UUIDv7
idt gen uuidv7
# Generate a ULID
idt gen ulid
# Generate a NanoID
idt gen nanoid
# Generate a Snowflake ID
idt gen snowflake
# Generate multiple IDs
idt gen uuid -n 10
Inspecting IDs
Analyze any ID with the inspect command:
# Inspect a UUID
idt inspect 550e8400-e29b-41d4-a716-446655440000
# Inspect a ULID
idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
# Auto-detection works for most formats
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469
Example output:
UUIDV7
019c04e5-6118-7b22-95cb-a10e84dad469
Time (UTC) 2026-01-28T13:57:47.416Z
Local Time (+09:00) 2026-01-28T22:57:47.416+09:00
Version 7
Variant RFC4122
Random 62 bits
Hex 019c04e561187b2295cba10e84dad469
Base64 AZwE5WEYeyKVy6EOhNrUaQ==
Int 2139325608653621017571381452845274217
Converting Formats
Convert IDs to different encodings:
# Convert to hexadecimal
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex
# Convert to Base64
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
# Convert to Base58
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base58
# Convert to integer
idt convert 550e8400-e29b-41d4-a716-446655440000 -f int
Validating IDs
Check if a string is a valid ID:
# Validate any ID
idt validate 550e8400-e29b-41d4-a716-446655440000
# Validate as specific type
idt validate -t uuid 550e8400-e29b-41d4-a716-446655440000
# Strict validation (canonical form only)
idt validate --strict 550e8400-e29b-41d4-a716-446655440000
Comparing IDs
Compare two IDs to understand their relationship:
idt compare 019c04e5-6118-7b22-95cb-a10e84dad469 019c04e5-6119-7000-8000-000000000000
This shows binary, lexicographic, and chronological comparisons.
Sorting IDs
Sort IDs by their embedded timestamps:
# Sort IDs chronologically
idt sort <ID>...
# Sort with timestamps displayed
idt sort --show-time <ID>...
# Sort newest first
idt sort --reverse <ID>...
# Pipe generated IDs through sort
idt gen ulid -n 5 | idt sort --show-time
Structured Output (JSON, YAML, TOML)
Get machine-readable output in multiple formats:
# JSON output
idt gen uuid --output json
idt gen uuid --json # shorthand
idt gen uuid -j # shorthand
# YAML output
idt inspect 550e8400-e29b-41d4-a716-446655440000 --output yaml
# TOML output
idt inspect 550e8400-e29b-41d4-a716-446655440000 --output toml
# Pretty-printed JSON
idt inspect 550e8400-e29b-41d4-a716-446655440000 --json --pretty
Piping and Scripting
idt works great with Unix pipes:
# Generate and immediately inspect
idt gen uuid | idt inspect
# Validate multiple IDs
idt gen ulid -n 100 | idt validate
# Convert piped input
echo "550e8400-e29b-41d4-a716-446655440000" | idt convert -f base64
Getting Help
View available commands and options:
# General help
idt --help
# Help for a specific command
idt gen --help
idt inspect --help
Next Steps
Commands Overview
idt provides the following commands for working with identifiers:
| Command | Alias | Description |
|---|---|---|
| gen | g | Generate new IDs |
| inspect | i | Analyze and decode IDs |
| convert | c | Convert between formats |
| validate | v | Check if input is valid |
| compare | - | Compare two IDs |
| sort | s | Sort IDs by timestamp |
| info | - | Show ID type information |
Global Options
These options work with all commands:
| Option | Description |
|---|---|
-j, --json | Output in JSON format |
-p, --pretty | Pretty-print JSON output |
--no-color | Disable colored output |
-h, --help | Show help information |
-V, --version | Show version |
Command Aliases
For faster typing, use command aliases:
idt g uuid # Same as: idt gen uuid
idt i <ID> # Same as: idt inspect <ID>
idt c <ID> -f hex # Same as: idt convert <ID> -f hex
idt v <ID> # Same as: idt validate <ID>
idt s <ID>... # Same as: idt sort <ID>...
Reading from stdin
Most commands that accept IDs can read from stdin:
# Pipe from another command
idt gen uuid | idt inspect
# Read from file
cat ids.txt | idt validate
# Here-string
idt inspect <<< "550e8400-e29b-41d4-a716-446655440000"
Exit Codes
Commands use standard exit codes:
| Code | Meaning |
|---|---|
| 0 | Success |
| 1 | Error (invalid input, validation failure, etc.) |
This makes idt suitable for use in scripts:
if idt validate -q "$ID"; then
echo "Valid ID"
else
echo "Invalid ID"
fi
gen - Generate IDs
Generate new identifiers of various types.
Usage
idt gen <TYPE> [OPTIONS]
Arguments
| Argument | Description |
|---|---|
TYPE | ID type to generate (uuid, uuidv7, ulid, nanoid, snowflake, etc.) |
Options
| Option | Description |
|---|---|
-n, --count <N> | Number of IDs to generate (default: 1) |
-f, --format <FORMAT> | Output encoding format |
-T, --template <TPL> | Wrap each ID in a template string ({} = placeholder) |
-o, --output <FORMAT> | Output format (json, yaml, toml) |
--no-newline | Don’t print trailing newline (single ID only) |
UUID Options
| Option | Description |
|---|---|
--uuid-version <V> | UUID version (1, 4, 6, 7) |
--namespace <NS> | Namespace for UUID v3/v5 (dns, url, oid, x500, or UUID) |
--name <NAME> | Name for UUID v3/v5 |
NanoID Options
| Option | Description |
|---|---|
--alphabet <CHARS> | Custom alphabet |
--length <N> | Custom length (default: 21) |
Snowflake Options
| Option | Description |
|---|---|
--preset <NAME> | Snowflake preset (twitter, discord, instagram, sonyflake, mastodon) |
--epoch <EPOCH> | Custom epoch (discord, twitter, or milliseconds since Unix epoch) |
--field <NAME=VALUE> | Set a Snowflake field value (e.g., --field shard_id=42) |
--machine-id <N> | Machine/worker ID (0-31 for Twitter/Discord, 0-65535 for Sonyflake) |
--datacenter-id <N> | Datacenter ID (0-31, Twitter/Discord layout only) |
Note:
--presetand--epochcannot be used together.
TypeID Options
| Option | Description |
|---|---|
--prefix <PREFIX> | Type prefix for TypeID |
Supported Types
| Type | Alias | Description |
|---|---|---|
uuid | - | UUIDv4 (random) by default |
uuidv1 | - | UUIDv1 (timestamp + MAC) |
uuidv4 | - | UUIDv4 (random) |
uuidv6 | - | UUIDv6 (reordered timestamp) |
uuidv7 | - | UUIDv7 (Unix timestamp + random) |
uuid-nil | - | Nil UUID (all zeros) |
uuid-max | - | Max UUID (all ones) |
ulid | - | ULID |
nanoid | - | NanoID |
snowflake | - | Snowflake ID |
Examples
Basic Generation
# Generate a random UUID (v4)
idt gen uuid
# Generate UUIDv7 (time-sortable)
idt gen uuidv7
# Generate ULID
idt gen ulid
# Generate NanoID
idt gen nanoid
# Generate Snowflake ID
idt gen snowflake
Multiple IDs
# Generate 10 UUIDs
idt gen uuid -n 10
# Generate 100 ULIDs
idt gen ulid -n 100
UUID Versions
# UUIDv1 (timestamp-based)
idt gen uuidv1
# UUIDv6 (reordered timestamp)
idt gen uuidv6
# UUIDv7 (Unix timestamp)
idt gen uuidv7
# Or use --uuid-version flag
idt gen uuid --uuid-version 7
NanoID Customization
# Custom length
idt gen nanoid --length 32
# Custom alphabet (hex characters only)
idt gen nanoid --alphabet "0123456789abcdef"
# Both
idt gen nanoid --length 16 --alphabet "0123456789ABCDEF"
Snowflake Customization
# Use a preset (layout + epoch + timestamp resolution)
idt gen snowflake --preset twitter
idt gen snowflake --preset discord
idt gen snowflake --preset instagram --field shard_id=42
idt gen snowflake --preset sonyflake # 10ms timestamp resolution
idt gen snowflake --preset mastodon
# With machine and datacenter IDs
idt gen snowflake --preset twitter --machine-id 1 --datacenter-id 2
# Backward-compatible epoch flag
idt gen snowflake --epoch discord
idt gen snowflake --epoch twitter
idt gen snowflake --epoch 1420070400000
Output Formats
# Generate and output as hex
idt gen uuid -f hex
# Generate and output as Base64
idt gen uuidv7 -f base64
# Save to file
idt gen uuid -n 1000 -o uuids.txt
Structured Output (JSON, YAML, TOML)
# Single ID as JSON
idt gen uuid --output json
# Output: {"id":"550e8400-e29b-41d4-a716-446655440000"}
# JSON shorthand
idt gen uuid --json
idt gen uuid -j
# Multiple IDs as JSON array
idt gen uuid -n 3 --output json
# Output: ["550e8400-...", "6ba7b810-...", "7c9e6679-..."]
# YAML output
idt gen uuid --output yaml
# Output: id: '550e8400-e29b-41d4-a716-446655440000'
# TOML output
idt gen uuid --output toml
# Output: id = "550e8400-e29b-41d4-a716-446655440000"
Template Output
# Wrap in SQL statement
idt gen uuidv7 -T 'INSERT INTO users (id) VALUES ("{}");'
# JSON fixture
idt gen uuidv7 -n 3 -T '{"id": "{}"}'
# Combined with format conversion
idt gen uuidv7 --format hex -T 'id={}'
Note:
--templatecannot be used with structured output formats (--json,--output). If the template does not contain{}, a warning is printed to stderr.
Without Trailing Newline
# Useful for scripting
ID=$(idt gen uuid --no-newline)
echo "Generated: $ID"
inspect - Analyze IDs
Analyze and decode identifiers to extract embedded information like timestamps, versions, and other metadata.
Usage
idt inspect [OPTIONS] [ID]...
Arguments
| Argument | Description |
|---|---|
ID | ID(s) to inspect (reads from stdin if omitted) |
Options
| Option | Description |
|---|---|
-t, --type <TYPE> | Hint the ID type (skip auto-detection) |
--epoch <EPOCH> | Epoch for Snowflake IDs (discord, twitter, or milliseconds since Unix epoch) |
--preset <NAME> | Snowflake preset (twitter, discord, instagram, sonyflake, mastodon) |
-q, --quiet | Only show errors (for validation use) |
Note:
--presetand--epochcannot be used together. Use--presetto get the correct bit layout, epoch, and timestamp resolution for a specific service.
Output Fields
When inspecting an ID, idt displays:
| Field | Description |
|---|---|
| Type | Detected ID type (e.g., UUIDV7, ULID) |
| Canonical | The ID in its canonical format |
| Time (UTC) | Embedded timestamp in UTC (if available) |
| Local Time | Timestamp in local timezone with UTC offset (if available) |
| Version | UUID version number (for UUIDs) |
| Variant | UUID variant (for UUIDs) |
| Random | Number of random bits |
| Hex | Hexadecimal encoding |
| Base64 | Base64 encoding |
| Int | Integer representation |
Examples
Basic Inspection
# Inspect a UUID
idt inspect 550e8400-e29b-41d4-a716-446655440000
# Inspect a ULID
idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
# Inspect multiple IDs
idt inspect 550e8400-e29b-41d4-a716-446655440000 01ARZ3NDEKTSV4RRFFQ69G5FAV
Example Output
$ idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469
UUIDV7
019c04e5-6118-7b22-95cb-a10e84dad469
Time (UTC) 2026-01-28T13:57:47.416Z
Local Time (+09:00) 2026-01-28T22:57:47.416+09:00
Version 7
Variant RFC4122
Random 62 bits
Hex 019c04e561187b2295cba10e84dad469
Base64 AZwE5WEYeyKVy6EOhNrUaQ==
Int 2139325608653621017571381452845274217
ULID Output
$ idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
ULID
01ARZ3NDEKTSV4RRFFQ69G5FAV
Time (UTC) 2016-07-30T23:54:10.259Z
Local Time (+09:00) 2016-07-31T08:54:10.259+09:00
Random 80 bits
Hex 01563e3ab5d3d6764c61efb99302bd5b
Base64 AVY+OrXT1nZMYe+5kwK9Ww==
Int 1777027686520646174104517696511196507
Type Hints
When auto-detection is ambiguous, provide a type hint:
# Force interpretation as UUID
idt inspect -t uuid 550e8400e29b41d4a716446655440000
Snowflake Presets
Different services use different Snowflake bit layouts, epochs, and timestamp resolutions. Use --preset to decode with the correct settings:
# Twitter Snowflake (41t + 5dc + 5worker + 12seq, ms)
idt inspect --preset twitter 1234567890123456789
# Discord Snowflake (same layout, different epoch)
idt inspect --preset discord 1474004412518240339
# Instagram Snowflake (41t + 13shard + 10seq)
idt inspect --preset instagram 1474004412518240339
# Sonyflake (39t + 8seq + 16machine, 10ms resolution)
idt inspect --preset sonyflake 610591162520043520
# Mastodon (48t + 16seq, Unix epoch)
idt inspect --preset mastodon 116226149176639488
Snowflake Epochs (backward compatible)
You can also use --epoch for backward compatibility. This uses the Twitter bit layout with a custom epoch:
# Discord Snowflake
idt inspect -t snowflake --epoch discord 1474004412518240339
# Twitter Snowflake
idt inspect -t snowflake --epoch twitter 1234567890123456789
# Custom epoch (milliseconds since Unix epoch)
idt inspect -t snowflake --epoch 1420070400000 1474004412518240339
Without --preset or --epoch, Snowflake IDs are decoded using the Unix epoch (0) and Twitter bit layout.
Reading from stdin
# Pipe from gen command
idt gen uuidv7 | idt inspect
# Read multiple IDs from file
cat ids.txt | idt inspect
# Here-string
idt inspect <<< "550e8400-e29b-41d4-a716-446655440000"
Structured Output (JSON, YAML, TOML)
# JSON output
idt inspect 550e8400-e29b-41d4-a716-446655440000 --output json
idt inspect 550e8400-e29b-41d4-a716-446655440000 --json # shorthand
idt inspect 550e8400-e29b-41d4-a716-446655440000 -j # shorthand
# Pretty-printed JSON
idt inspect 550e8400-e29b-41d4-a716-446655440000 --json --pretty
# YAML output
idt inspect 550e8400-e29b-41d4-a716-446655440000 --output yaml
# TOML output
idt inspect 550e8400-e29b-41d4-a716-446655440000 --output toml
Example JSON output:
{
"id_type": "uuidv4",
"canonical": "550e8400-e29b-41d4-a716-446655440000",
"valid": true,
"version": "4",
"variant": "RFC4122",
"random_bits": 122,
"encodings": {
"hex": "550e8400e29b41d4a716446655440000",
"base64": "VQ6EAOKbQdSnFkRmVUQAAA==",
"int": "113059749145936325402354257176981405696"
}
}
For timestamped IDs, additional fields are included:
{
"timestamp": { "millis": 1706450267416 },
"timestamp_iso": "2026-01-28T13:57:47.416Z",
"timestamp_local_iso": "2026-01-28T22:57:47.416+09:00"
}
Quiet Mode
Quiet mode exits with code 0 for valid IDs, 1 for invalid:
if idt inspect -q "$ID" 2>/dev/null; then
echo "Valid and parseable"
fi
Inspecting Generated IDs
# Generate and inspect in one pipeline
idt gen uuidv7 | idt inspect
# Generate multiple and inspect
idt gen ulid -n 5 | idt inspect
convert - Convert Formats
Convert identifiers between different encoding formats.
Usage
idt convert [OPTIONS] [ID]...
Arguments
| Argument | Description |
|---|---|
ID | ID(s) to convert (reads from stdin if omitted) |
Options
| Option | Description |
|---|---|
-t, --type <TYPE> | Source ID type (auto-detect if omitted) |
-f, --format <FORMAT> | Target encoding format |
--to <TYPE> | Convert to different ID type (if compatible) |
-U, --uppercase | Uppercase output |
-L, --lowercase | Lowercase output |
Encoding Formats
| Format | Description | Example |
|---|---|---|
canonical | Original format | 550e8400-e29b-41d4-a716-446655440000 |
hex | Hexadecimal | 550e8400e29b41d4a716446655440000 |
base32 | Base32 (RFC 4648) | KUHIBAASSNE5JJYWIRDFKRAAAA |
base58 | Base58 | 6K8FVbLqP4V8nDqTJNXH6k |
base64 | Base64 | VQ6EAOKbQdSnFkRmVUQAAA== |
base64url | URL-safe Base64 | VQ6EAOKbQdSnFkRmVUQAAA |
bits | Binary string | 01010101000011101000... |
int | Integer | 113059749145936325402354257176981405696 |
bytes | Space-separated hex bytes | 55 0e 84 00 e2 9b 41 d4... |
Examples
Basic Conversion
# Convert to hex
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex
# Output: 550e8400e29b41d4a716446655440000
# Convert to Base64
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
# Output: VQ6EAOKbQdSnFkRmVUQAAA==
# Convert to Base58
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base58
# Output: 6K8FVbLqP4V8nDqTJNXH6k
# Convert to integer
idt convert 550e8400-e29b-41d4-a716-446655440000 -f int
# Output: 113059749145936325402354257176981405696
Case Transformation
# Uppercase hex
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex -U
# Output: 550E8400E29B41D4A716446655440000
# Lowercase
idt convert 550E8400-E29B-41D4-A716-446655440000 -f hex -L
# Output: 550e8400e29b41d4a716446655440000
Converting ULID
# ULID to hex
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f hex
# Output: 01563e3ab5d3d6764c61efb99302bd5b
# ULID to Base64
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f base64
# Output: AVY+OrXT1nZMYe+5kwK9Ww==
Binary Representation
# Convert to binary string
idt convert 550e8400-e29b-41d4-a716-446655440000 -f bits
# Output: 01010101000011101000010000000000111000101001101101000001110101001010011100010110010001000110011001010101010001000000000000000000
# Convert to space-separated bytes
idt convert 550e8400-e29b-41d4-a716-446655440000 -f bytes
# Output: 55 0e 84 00 e2 9b 41 d4 a7 16 44 66 55 44 00 00
URL-Safe Base64
# Standard Base64 (with padding)
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
# Output: VQ6EAOKbQdSnFkRmVUQAAA==
# URL-safe Base64 (no padding)
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64url
# Output: VQ6EAOKbQdSnFkRmVUQAAA
Reading from stdin
# Pipe from gen
idt gen uuid | idt convert -f base64
# Possible output: dkIwdr8eQ+WS5BaKwkF55g==
# Convert multiple IDs
echo -e "550e8400-e29b-41d4-a716-446655440000\n6ba7b810-9dad-11d1-80b4-00c04fd430c8" | idt convert -f hex
# Output:
# 550e8400e29b41d4a716446655440000
# 6ba7b8109dad11d180b400c04fd430c8
Structured Output (JSON, YAML, TOML)
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex --output json
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex --json # shorthand
# Output: "550e8400e29b41d4a716446655440000"
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex --output yaml
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex --output toml
Type Hints
For ambiguous inputs, specify the source type:
# Interpret as UUID (no dashes)
idt convert -t uuid 550e8400e29b41d4a716446655440000 -f canonical
# Output: 550e8400-e29b-41d4-a716-446655440000
validate - Validate IDs
Check if input strings are valid identifiers.
Usage
idt validate [OPTIONS] [ID]...
Arguments
| Argument | Description |
|---|---|
ID | ID(s) to validate (reads from stdin if omitted) |
Options
| Option | Description |
|---|---|
-t, --type <TYPE> | Expected ID type (any valid if omitted) |
-q, --quiet | No output, only exit code |
--strict | Strict validation (reject non-canonical forms) |
Exit Codes
| Code | Meaning |
|---|---|
| 0 | All IDs are valid |
| 1 | One or more IDs are invalid |
Examples
Basic Validation
# Validate a UUID
idt validate 550e8400-e29b-41d4-a716-446655440000
# Output: 550e8400-e29b-41d4-a716-446655440000: valid (uuidv4)
# Validate a ULID
idt validate 01ARZ3NDEKTSV4RRFFQ69G5FAV
# Output: 01ARZ3NDEKTSV4RRFFQ69G5FAV: valid (ulid)
# Invalid ID
idt validate not-a-valid-id
# Output: not-a-valid-id: invalid
# Error: Not a recognized ID format
Type-Specific Validation
# Must be a UUID
idt validate -t uuid 550e8400-e29b-41d4-a716-446655440000
# Output: valid (uuid)
# Must be a ULID
idt validate -t ulid 01ARZ3NDEKTSV4RRFFQ69G5FAV
# Output: valid (ulid)
# Wrong type
idt validate -t ulid 550e8400-e29b-41d4-a716-446655440000
# Output: invalid (expected ulid)
Assigned IDs
Validate product, publication, and financial identifiers:
# EAN-13 barcode
idt validate -t ean13 4006381333931
# Output: 4006381333931: valid (ean13)
# ISBN-13 (with or without hyphens)
idt validate -t isbn13 978-0-306-40615-7
# Output: 978-0-306-40615-7: valid (isbn13)
# ISBN-10 (check digit can be X)
idt validate -t isbn10 080442957X
# Output: 080442957X: valid (isbn10)
# ISIN (securities identifier)
idt validate -t isin US0378331005
# Output: US0378331005: valid (isin)
# EAN-8 barcode
idt validate -t ean8 96385074
# UPC-A barcode
idt validate -t upca 036000291452
# ISSN (serial publications)
idt validate -t issn 0378-5955
# ISMN (music publications)
idt validate -t ismn 979-0-060-11561-5
# ISNI (name identifiers)
idt validate -t isni "0000 0001 2103 2683"
# GTIN-14 (trade items)
idt validate -t gtin14 10614141000415
# ASIN (Amazon products)
idt validate -t asin B08N5WRWNW
# Auto-detection also works
idt validate 9780306406157
# Output: 9780306406157: valid (isbn13)
Strict Mode
Strict mode rejects non-canonical forms:
# Canonical form - passes
idt validate --strict 550e8400-e29b-41d4-a716-446655440000
# Uppercase - fails strict validation
idt validate --strict 550E8400-E29B-41D4-A716-446655440000
# Output: invalid
# Error: Non-canonical form
# Hint: Canonical form: 550e8400-e29b-41d4-a716-446655440000
Quiet Mode
For scripting, use quiet mode to check exit codes only:
# Check if valid
if idt validate -q "$ID"; then
echo "Valid ID: $ID"
else
echo "Invalid ID: $ID"
fi
# Validate and continue only if valid
idt validate -q "$ID" && process_id "$ID"
Validating Multiple IDs
# Multiple arguments
idt validate id1 id2 id3
# From file
cat ids.txt | idt validate
# From generated IDs
idt gen uuid -n 100 | idt validate
Helpful Hints
idt provides hints for common mistakes:
# UUID without dashes
idt validate 550e8400e29b41d4a716446655440000
# Output: invalid
# Hint: Looks like UUID without dashes. Try adding dashes.
# Invalid characters in UUID
idt validate 550e8400-e29b-41d4-a716-44665544000g
# Output: invalid
# Hint: Check for invalid characters in UUID.
Structured Output (JSON, YAML, TOML)
# JSON output
idt validate 550e8400-e29b-41d4-a716-446655440000 --output json
idt validate 550e8400-e29b-41d4-a716-446655440000 --json # shorthand
# Output: {"input":"550e8400-...","valid":true,"id_type":"uuidv4"}
# YAML output
idt validate 550e8400-e29b-41d4-a716-446655440000 --output yaml
# TOML output
idt validate 550e8400-e29b-41d4-a716-446655440000 --output toml
# Multiple IDs
idt validate id1 id2 --json
# Output: [{"input":"id1",...},{"input":"id2",...}]
Batch Validation
Validate a file of IDs:
# Count valid/invalid
cat ids.txt | idt validate 2>&1 | grep -c "valid"
# Extract only valid IDs
cat ids.txt | while read id; do
if idt validate -q "$id" 2>/dev/null; then
echo "$id"
fi
done
compare - Compare IDs
Compare two identifiers to understand their relationship in terms of binary ordering, lexicographic ordering, and chronological ordering (for time-based IDs).
Usage
idt compare [OPTIONS] <ID1> <ID2>
Arguments
| Argument | Description |
|---|---|
ID1 | First ID to compare |
ID2 | Second ID to compare |
Options
| Option | Description |
|---|---|
-t, --type <TYPE> | ID type (auto-detect if omitted) |
Comparison Types
| Comparison | Description |
|---|---|
| Binary | Byte-by-byte comparison of raw ID data |
| Lexicographic | String comparison of canonical forms |
| Chronological | Time comparison (for time-based IDs) |
Examples
Basic Comparison
idt compare 019c04e5-6118-7b22-95cb-a10e84dad469 019c04e5-6119-7000-8000-000000000000
Output:
Comparing IDs:
ID 1: 019c04e5-6118-7b22-95cb-a10e84dad469
ID 2: 019c04e5-6119-7000-8000-000000000000
Comparison Results:
Binary: ID1 < ID2
Lexicographic: ID1 < ID2
Chronological: ID1 is older (created before ID2)
Time difference: 1.00 seconds
Comparing Different Types
idt compare 01ARZ3NDEKTSV4RRFFQ69G5FAV 01ARZ3NDEKTSV4RRFFQ69G5FAW
When comparing IDs of different types, idt warns you:
idt compare 550e8400-e29b-41d4-a716-446655440000 01ARZ3NDEKTSV4RRFFQ69G5FAV
Output:
Comparing IDs:
ID 1: 550e8400-e29b-41d4-a716-446655440000
ID 2: 01ARZ3NDEKTSV4RRFFQ69G5FAV
Warning: Different types! (uuidv4 vs ulid)
Comparison Results:
Binary: ID1 > ID2
Lexicographic: ID1 > ID2
Time-Based Comparison
For IDs with timestamps (UUIDv1, UUIDv6, UUIDv7, ULID, Snowflake), idt shows chronological comparison:
# Generate two UUIDv7s with a delay
ID1=$(idt gen uuidv7)
sleep 2
ID2=$(idt gen uuidv7)
idt compare "$ID1" "$ID2"
Output:
Comparison Results:
Binary: ID1 < ID2
Lexicographic: ID1 < ID2
Chronological: ID1 is older (created before ID2)
Time difference: 2.00 seconds
Comparison Symbols
The output uses comparison symbols:
| Symbol | Meaning |
|---|---|
< | ID1 is less than ID2 |
> | ID1 is greater than ID2 |
= | IDs are equal |
Structured Output (JSON, YAML, TOML)
idt compare id1 id2 --output json
idt compare id1 id2 --json # shorthand
idt compare id1 id2 --output yaml
idt compare id1 id2 --output toml
Output:
{
"id1": "019c04e5-6118-7b22-95cb-a10e84dad469",
"id2": "019c04e5-6119-7000-8000-000000000000",
"type1": "uuidv7",
"type2": "uuidv7",
"binary_order": "less",
"lexicographic_order": "less",
"chronological_order": "less",
"time_diff_ms": 1000,
"timestamp1": 1706450267416,
"timestamp2": 1706450268416
}
Use Cases
Verify sortability:
# Check if time-sortable IDs maintain order
idt compare "$OLDER_ID" "$NEWER_ID"
# Should show: ID1 < ID2 for all comparisons
Debug ordering issues:
# When IDs aren't sorting as expected
idt compare "$ID_A" "$ID_B" --json | jq '.binary_order, .lexicographic_order'
Time difference calculation:
# Find time between two events
idt compare "$START_ID" "$END_ID" --json | jq '.time_diff_ms'
sort - Sort IDs by Timestamp
Sort a list of IDs by their embedded timestamps. Useful when debugging distributed systems, analyzing logs, or working with database records where you need to understand temporal ordering.
Usage
idt sort [OPTIONS] [ID...]
Arguments
| Argument | Description |
|---|---|
ID... | IDs to sort (reads from stdin if omitted) |
Options
| Option | Description |
|---|---|
-t, --id-type <TYPE> | ID type hint (skip auto-detection) |
-r, --reverse | Sort in descending order (newest first) |
--show-time | Display timestamps alongside IDs |
--epoch <EPOCH> | Snowflake epoch (discord, twitter, or milliseconds) |
--preset <NAME> | Snowflake preset (twitter, discord, instagram, sonyflake, mastodon) |
--on-unsortable <POLICY> | Policy for IDs without timestamps: skip (default), error, end |
Examples
Basic Sorting
# Sort ULIDs by creation time
idt sort 01KK3ZE8GEVTC9PGC0NTY1RY03 01ARZ3NDEKTSV4RRFFQ69G5FAV
Output:
01ARZ3NDEKTSV4RRFFQ69G5FAV
01KK3ZE8GEVTC9PGC0NTY1RY03
Show Timestamps
idt sort --show-time 01KK3ZE8GEVTC9PGC0NTY1RY03 01ARZ3NDEKTSV4RRFFQ69G5FAV
Output:
2016-07-30T23:54:10.259Z 01ARZ3NDEKTSV4RRFFQ69G5FAV
2026-03-07T11:03:08.046Z 01KK3ZE8GEVTC9PGC0NTY1RY03
Reverse Order (Newest First)
idt sort --reverse --show-time 01ARZ3NDEKTSV4RRFFQ69G5FAV 01KK3ZE8GEVTC9PGC0NTY1RY03
Output:
2026-03-07T11:03:08.046Z 01KK3ZE8GEVTC9PGC0NTY1RY03
2016-07-30T23:54:10.259Z 01ARZ3NDEKTSV4RRFFQ69G5FAV
Pipe from Generation
# Generate 5 ULIDs and sort them with timestamps
idt gen ulid -n 5 | idt sort --show-time
Mixed ID Types
IDs of different types can be sorted together as long as they have timestamps:
# Sort a mix of UUIDv7 and ULID
idt sort 019c04e5-6118-7b22-95cb-a10e84dad469 01ARZ3NDEKTSV4RRFFQ69G5FAV
Structured Output (JSON, YAML, TOML)
idt sort --output json --pretty 01ARZ3NDEKTSV4RRFFQ69G5FAV 01KK3ZE8GEVTC9PGC0NTY1RY03
idt sort --json --pretty 01ARZ3NDEKTSV4RRFFQ69G5FAV 01KK3ZE8GEVTC9PGC0NTY1RY03 # shorthand
idt sort --output yaml 01ARZ3NDEKTSV4RRFFQ69G5FAV 01KK3ZE8GEVTC9PGC0NTY1RY03
idt sort --output toml 01ARZ3NDEKTSV4RRFFQ69G5FAV 01KK3ZE8GEVTC9PGC0NTY1RY03
Output:
{
"sorted": [
{
"id": "01ARZ3NDEKTSV4RRFFQ69G5FAV",
"id_type": "ulid",
"timestamp_ms": 1469922850259,
"timestamp_iso": "2016-07-30T23:54:10.259Z"
},
{
"id": "01KK3ZE8GEVTC9PGC0NTY1RY03",
"id_type": "ulid",
"timestamp_ms": 1772881388046,
"timestamp_iso": "2026-03-07T11:03:08.046Z"
}
],
"unsortable": [],
"count": 2
}
Unsortable ID Policies
Some ID types (NanoID, CUID2, UUIDv4) don’t have embedded timestamps. The --on-unsortable option controls how these are handled:
| Policy | Behavior |
|---|---|
skip (default) | Skip the ID with a warning to stderr |
error | Fail immediately with an error |
end | Append unsortable IDs after the sorted ones |
# Skip unsortable IDs (default)
idt sort 01ARZ3NDEKTSV4RRFFQ69G5FAV some-nanoid-value
# Fail on unsortable IDs
idt sort --on-unsortable error 01ARZ3NDEKTSV4RRFFQ69G5FAV some-nanoid-value
# Append unsortable IDs at the end
idt sort --on-unsortable end 01ARZ3NDEKTSV4RRFFQ69G5FAV some-nanoid-value
Use Cases
Order log entries by creation time:
cat log_ids.txt | idt sort --show-time
Find the newest/oldest ID:
# Oldest
cat ids.txt | idt sort | head -1
# Newest
cat ids.txt | idt sort --reverse | head -1
Timeline reconstruction:
cat event_ids.txt | idt sort --show-time --output json | jq '.sorted[] | "\(.timestamp_iso) \(.id)"'
info - ID Type Information
Display information about supported ID types, including their characteristics, specifications, and usage notes.
Usage
idt info [TYPE]
Arguments
| Argument | Description |
|---|---|
TYPE | ID type to get information about (list all if omitted) |
Examples
List All Types
idt info
Output:
Supported ID Types
============================================================
UUID Family:
uuidv1 [T-] Timestamp + MAC address
uuidv3 [--] MD5 namespace hash
uuidv4 [--] Random
uuidv5 [--] SHA-1 namespace hash
uuidv6 [TS] Reordered timestamp
uuidv7 [TS] Unix timestamp + random
uuid-nil [--] All zeros
uuid-max [--] All ones
Modern Sortable IDs:
ulid [TS] Crockford Base32, lexicographically sortable
snowflake [TS] Twitter/Discord-style distributed ID
Compact IDs:
nanoid [--] Compact URL-friendly ID
Use 'idt info <TYPE>' for detailed information.
The flags in brackets indicate:
T= Has timestampS= Sortable-= No/Not applicable
Detailed Type Information
idt info uuidv7
Output:
UUIDV7
============================================================
Unix timestamp + random
Has Timestamp: Yes
Sortable: Yes
Bit Length: 128 bits
Example: 019c04e5-6118-7b22-95cb-a10e84dad469
Specification: https://datatracker.ietf.org/doc/html/rfc9562
Notes:
- Recommended for new applications needing sortable UUIDs
- Unix timestamp in milliseconds
- Compatible with UUID infrastructure
Other Type Examples
idt info ulid
Output:
ULID
============================================================
Crockford Base32, lexicographically sortable
Has Timestamp: Yes
Sortable: Yes
Bit Length: 128 bits
Example: 01ARZ3NDEKTSV4RRFFQ69G5FAV
Specification: https://github.com/ulid/spec
Notes:
- Case-insensitive (Crockford Base32)
- Monotonic within same millisecond
- Compatible with UUID (128-bit)
idt info snowflake
Output:
SNOWFLAKE
============================================================
Twitter/Discord-style distributed ID
Has Timestamp: Yes
Sortable: Yes
Bit Length: 64 bits
Example: 1234567890123456789
Specification: https://en.wikipedia.org/wiki/Snowflake_ID
Notes:
- Originally designed by Twitter
- Requires coordination (machine/datacenter IDs)
- Epoch can be customized
Structured Output (JSON, YAML, TOML)
# All types as JSON
idt info --output json
idt info --json # shorthand
# Specific type as JSON
idt info uuidv7 --json
# YAML output
idt info uuidv7 --output yaml
# TOML output
idt info uuidv7 --output toml
Example JSON output:
{
"name": "uuidv7",
"description": "Unix timestamp + random",
"has_timestamp": true,
"is_sortable": true,
"bit_length": 128,
"example": "019c04e5-6118-7b22-95cb-a10e84dad469",
"spec_url": "https://datatracker.ietf.org/doc/html/rfc9562",
"notes": [
"Recommended for new applications needing sortable UUIDs",
"Unix timestamp in milliseconds",
"Compatible with UUID infrastructure"
]
}
Querying Capabilities
Use JSON output to query capabilities programmatically:
# List all sortable types
idt info --json | jq '.[] | select(.is_sortable) | .name'
# List all types with timestamps
idt info --json | jq '.[] | select(.has_timestamp) | .name'
# Get bit length of a type
idt info uuidv7 --json | jq '.bit_length'
ID Types Overview
idt supports a wide variety of identifier formats, from the ubiquitous UUID to modern alternatives like ULID and Snowflake IDs.
Quick Comparison
| Type | Bits | Sortable | Timestamp | Format |
|---|---|---|---|---|
| UUIDv1 | 128 | No | Yes | xxxxxxxx-xxxx-1xxx-xxxx-xxxxxxxxxxxx |
| UUIDv4 | 128 | No | No | xxxxxxxx-xxxx-4xxx-xxxx-xxxxxxxxxxxx |
| UUIDv6 | 128 | Yes | Yes | xxxxxxxx-xxxx-6xxx-xxxx-xxxxxxxxxxxx |
| UUIDv7 | 128 | Yes | Yes | xxxxxxxx-xxxx-7xxx-xxxx-xxxxxxxxxxxx |
| ULID | 128 | Yes | Yes | 01ARZ3NDEKTSV4RRFFQ69G5FAV |
| NanoID | ~126 | No | No | V1StGXR8_Z5jdHi6B-myT |
| Snowflake | 64 | Yes | Yes | 1234567890123456789 |
| KSUID | 160 | Yes | Yes | 0ujsswThIGTUYm2K8FjOOfXtY1K |
| ObjectId | 96 | Partial | Yes | 507f1f77bcf86cd799439011 |
Choosing an ID Type
For New Projects
Recommended: UUIDv7 or ULID
Both provide:
- Time-sortable ordering
- Embedded timestamps
- 128-bit uniqueness
- Wide compatibility
Choose UUIDv7 if you need UUID compatibility (existing databases, APIs). Choose ULID if you want a more compact string representation.
For Distributed Systems
Recommended: Snowflake ID
- 64-bit (fits in a long integer)
- Extremely high throughput
- Guaranteed ordering within a datacenter
- Requires coordination (machine/datacenter IDs)
For URL-Safe Short IDs
Recommended: NanoID
- Customizable length and alphabet
- URL-safe by default
- No timestamp (pure random)
For Legacy Compatibility
UUIDv4 remains the most widely supported format.
ID Type Categories
UUID Family
The UUID (Universally Unique Identifier) family includes several versions, each with different generation strategies:
- UUID Family - UUIDv1, v3, v4, v5, v6, v7, nil, max
Modern Sortable IDs
These formats were designed specifically for modern distributed systems:
- ULID - Universally Unique Lexicographically Sortable Identifier
- Snowflake ID - Twitter/Discord-style distributed ID
Compact IDs
Shorter identifiers for specific use cases:
- NanoID - Compact, URL-friendly identifier
Other Formats
Additional ID formats supported by idt:
- Other ID Types - KSUID, ObjectId, TypeID, XID, CUID, TSID
Assigned IDs
Product, publication, and financial identifiers (validate and inspect only — not generated):
- Assigned IDs - EAN-13, ISBN-13, ISBN-10, ISIN
Generation Support
Not all ID types can be generated by idt. Here’s what’s supported:
| Type | Generate | Inspect | Convert | Validate |
|---|---|---|---|---|
| UUIDv1 | Yes | Yes | Yes | Yes |
| UUIDv4 | Yes | Yes | Yes | Yes |
| UUIDv6 | Yes | Yes | Yes | Yes |
| UUIDv7 | Yes | Yes | Yes | Yes |
| UUID-nil | Yes | Yes | Yes | Yes |
| UUID-max | Yes | Yes | Yes | Yes |
| ULID | Yes | Yes | Yes | Yes |
| NanoID | Yes | Yes | Yes | Yes |
| Snowflake | Yes | Yes | Yes | Yes |
| EAN-13 | No | Yes | Yes | Yes |
| ISBN-13 | No | Yes | Yes | Yes |
| ISBN-10 | No | Yes | Yes | Yes |
| ISIN | No | Yes | Yes | Yes |
Further Reading
- UUID Family - Detailed UUID version information
- ULID - ULID specification and usage
- NanoID - NanoID customization options
- Snowflake ID - Distributed ID generation
- Other ID Types - Additional formats
- Assigned IDs - EAN-13, ISBN-13, ISBN-10, ISIN
UUID Family
UUID (Universally Unique Identifier) is a 128-bit identifier standardized by RFC 4122 and updated by RFC 9562. UUIDs are the most widely used identifier format.
Format
All UUIDs share the same canonical format:
xxxxxxxx-xxxx-Mxxx-Nxxx-xxxxxxxxxxxx
Where:
Mindicates the version (1-8)Nindicates the variant (usually 8, 9, a, or b for RFC 4122)
Example: 550e8400-e29b-41d4-a716-446655440000
Versions
UUIDv1 - Timestamp + MAC Address
- Specification: RFC 4122
- Timestamp: Yes (100-nanosecond intervals since October 15, 1582)
- Sortable: No (timestamp is split across the ID)
- Privacy: Contains MAC address
idt gen uuidv1
# Example: 6ba7b810-9dad-11d1-80b4-00c04fd430c8
Structure:
- Time-low (32 bits)
- Time-mid (16 bits)
- Version + Time-high (16 bits)
- Variant + Clock sequence (16 bits)
- Node/MAC address (48 bits)
UUIDv3 - MD5 Namespace Hash
- Specification: RFC 4122
- Timestamp: No
- Sortable: No
- Deterministic: Yes (same namespace + name = same UUID)
# Currently generation is not supported
# Useful for inspecting existing UUIDv3s
idt inspect 5df41881-3aed-3515-88a7-2f4a814cf09e
UUIDv4 - Random
- Specification: RFC 4122
- Timestamp: No
- Sortable: No
- Random bits: 122
The most commonly used UUID version. Purely random except for version and variant bits.
idt gen uuid
# or
idt gen uuidv4
# Example: 550e8400-e29b-41d4-a716-446655440000
Collision probability: With 122 random bits, you’d need to generate about 2.71 quintillion UUIDs to have a 50% chance of collision.
UUIDv5 - SHA-1 Namespace Hash
- Specification: RFC 4122
- Timestamp: No
- Sortable: No
- Deterministic: Yes (same namespace + name = same UUID)
Similar to UUIDv3 but uses SHA-1 instead of MD5.
# Currently generation is not supported
# Useful for inspecting existing UUIDv5s
idt inspect 21f7f8de-8051-5b89-8680-0195ef798b6a
UUIDv6 - Reordered Timestamp
- Specification: RFC 9562
- Timestamp: Yes (same resolution as v1)
- Sortable: Yes
- Privacy: Contains MAC address (like v1)
Reorders v1’s timestamp bits for lexicographic sorting.
idt gen uuidv6
# Example: 1ec9414c-232a-6b00-b3c8-9e6bdeced846
When to use: When you need v1 compatibility but want sortable IDs.
UUIDv7 - Unix Timestamp + Random
- Specification: RFC 9562
- Timestamp: Yes (Unix milliseconds)
- Sortable: Yes
- Random bits: 62
- Recommended: Yes, for new applications
The recommended choice for new applications needing sortable UUIDs.
idt gen uuidv7
# Example: 019c04e5-6118-7b22-95cb-a10e84dad469
Structure:
- Unix timestamp in milliseconds (48 bits)
- Version (4 bits)
- Random (12 bits)
- Variant (2 bits)
- Random (62 bits)
Advantages:
- Naturally sorted by creation time
- Compatible with existing UUID infrastructure
- No MAC address (privacy-friendly)
- Sufficient randomness to avoid collisions
UUID-nil - All Zeros
The nil UUID is all zeros, often used as a placeholder or “no value” indicator.
idt gen uuid-nil
# Output: 00000000-0000-0000-0000-000000000000
UUID-max - All Ones
The max UUID is all ones, sometimes used as a sentinel value.
idt gen uuid-max
# Output: ffffffff-ffff-ffff-ffff-ffffffffffff
Inspecting UUIDs
$ idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469
UUIDV7
019c04e5-6118-7b22-95cb-a10e84dad469
Time (UTC) 2026-01-28T13:57:47.416Z
Local Time (+09:00) 2026-01-28T22:57:47.416+09:00
Version 7
Variant RFC4122
Random 62 bits
Hex 019c04e561187b2295cba10e84dad469
Base64 AZwE5WEYeyKVy6EOhNrUaQ==
Int 2139325608653621017571381452845274217
Converting UUIDs
# Remove dashes
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex
# To Base64
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
# To integer
idt convert 550e8400-e29b-41d4-a716-446655440000 -f int
Choosing a UUID Version
| Use Case | Recommended Version |
|---|---|
| General purpose, no special requirements | UUIDv4 |
| Need sortable IDs | UUIDv7 |
| Deterministic IDs from names | UUIDv5 |
| Legacy system compatibility | UUIDv1 |
| Sortable + v1 compatibility | UUIDv6 |
Specifications
- RFC 4122: Original UUID specification (v1-v5)
- https://datatracker.ietf.org/doc/html/rfc4122
- RFC 9562: New UUID formats (v6-v8)
- https://datatracker.ietf.org/doc/html/rfc9562
ULID
ULID (Universally Unique Lexicographically Sortable Identifier) is a 128-bit identifier designed for distributed systems that need sortable, URL-friendly IDs.
Overview
| Property | Value |
|---|---|
| Bits | 128 |
| Sortable | Yes |
| Timestamp | Yes (millisecond precision) |
| Format | Crockford Base32 |
| Length | 26 characters |
Format
01ARZ3NDEKTSV4RRFFQ69G5FAV
|----------|--------------|
Timestamp Random
(48 bits) (80 bits)
Example: 01ARZ3NDEKTSV4RRFFQ69G5FAV
Characteristics
Time-Sortable
ULIDs sort lexicographically in chronological order:
$ idt gen ulid
01ARZ3NDEKTSV4RRFFQ69G5FAV
$ idt gen ulid
01ARZ3NDEKTSV4RRFFQ69G5FAW
The second ULID will always sort after the first.
Monotonic
Within the same millisecond, ULIDs increment the random component to maintain ordering:
# Generated in same millisecond
01ARZ3NDEKTSV4RRFFQ69G5FAV
01ARZ3NDEKTSV4RRFFQ69G5FAW # Random incremented
01ARZ3NDEKTSV4RRFFQ69G5FAX # Random incremented again
Case-Insensitive
ULIDs use Crockford Base32, which is case-insensitive:
# These are equivalent
idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
idt inspect 01arz3ndektsv4rrffq69g5fav
URL-Safe
The Crockford Base32 alphabet excludes ambiguous characters (I, L, O, U) and is URL-safe.
Generation
# Generate a ULID
idt gen ulid
# Generate multiple ULIDs
idt gen ulid -n 10
Inspection
$ idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
ULID
01ARZ3NDEKTSV4RRFFQ69G5FAV
Time (UTC) 2016-07-30T23:54:10.259Z
Local Time (+09:00) 2016-07-31T08:54:10.259+09:00
Random 80 bits
Hex 01563e3ab5d3d6764c61efb99302bd5b
Base64 AVY+OrXT1nZMYe+5kwK9Ww==
Int 1777027686520646174104517696511196507
Conversion
ULID to UUID
ULIDs are 128-bit and can be converted to UUID format:
# Get hex representation (same as UUID without dashes)
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f hex
# Output: 01563e3ab5d3d6764c61efb99302bd5b
To Other Formats
# Base64
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f base64
# Integer
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f int
# Binary
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f bits
Comparison with UUID
| Feature | ULID | UUIDv4 | UUIDv7 |
|---|---|---|---|
| Bits | 128 | 128 | 128 |
| Sortable | Yes | No | Yes |
| Timestamp | Yes | No | Yes |
| String length | 26 | 36 | 36 |
| Case-sensitive | No | No | No |
| URL-safe | Yes | With encoding | With encoding |
When to Use ULID
Good for:
- Database primary keys (sortable, compact)
- Distributed systems needing time-ordered IDs
- URLs and APIs (shorter than UUID)
- Any use case needing sortable unique IDs
Consider alternatives if:
- You need UUID compatibility (use UUIDv7)
- You need sub-millisecond precision
- You need 64-bit IDs (use Snowflake)
Specification
- GitHub: https://github.com/ulid/spec
Crockford Base32 Alphabet
0123456789ABCDEFGHJKMNPQRSTVWXYZ
Excludes: I, L, O, U (to avoid confusion with 1, 1, 0, V)
NanoID
NanoID is a tiny, secure, URL-friendly unique string ID generator. It’s designed to be compact while maintaining sufficient uniqueness for most use cases.
Overview
| Property | Value |
|---|---|
| Default bits | ~126 |
| Sortable | No |
| Timestamp | No |
| Default length | 21 characters |
| Customizable | Yes (alphabet and length) |
Format
V1StGXR8_Z5jdHi6B-myT
|---------------------|
21 random characters
Example: V1StGXR8_Z5jdHi6B-myT
Characteristics
URL-Safe
The default alphabet is URL-safe:
A-Za-z0-9_-
No encoding needed when used in URLs.
Compact
At 21 characters, NanoID is shorter than UUID (36 chars) and ULID (26 chars).
Customizable
Both alphabet and length can be customized:
# Custom length
idt gen nanoid --length 32
# Custom alphabet
idt gen nanoid --alphabet "0123456789abcdef"
# Both
idt gen nanoid --length 16 --alphabet "ABCDEFGHIJKLMNOP"
Secure
Uses cryptographically secure random number generation.
Generation
# Default NanoID (21 characters)
idt gen nanoid
# Longer NanoID
idt gen nanoid --length 32
# Multiple NanoIDs
idt gen nanoid -n 10
Custom Alphabets
# Hex characters only
idt gen nanoid --alphabet "0123456789abcdef"
# Numbers only
idt gen nanoid --alphabet "0123456789"
# Lowercase letters only
idt gen nanoid --alphabet "abcdefghijklmnopqrstuvwxyz"
# Alphanumeric (no special chars)
idt gen nanoid --alphabet "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"
Inspection
$ idt inspect V1StGXR8_Z5jdHi6B-myT
NANOID
V1StGXR8_Z5jdHi6B-myT
Hex ...
Base64 ...
Note: NanoID doesn’t embed timestamps or other structured data.
Collision Probability
With default settings (21 characters, 64-character alphabet):
- ~126 bits of entropy
- For 1% collision probability: ~149 billion IDs
- For 50% collision probability: ~2.4 trillion IDs
Adjusting for Your Needs
Use this formula to calculate collision probability:
bits = log2(alphabet_size) * length
Examples:
- 21 chars, 64 alphabet: ~126 bits
- 32 chars, 64 alphabet: ~192 bits
- 16 chars, 16 alphabet (hex): ~64 bits
Comparison with Other IDs
| Feature | NanoID | UUID | ULID |
|---|---|---|---|
| Length | 21 | 36 | 26 |
| Sortable | No | No* | Yes |
| Timestamp | No | No* | Yes |
| URL-safe | Yes | No | Yes |
| Customizable | Yes | No | No |
*UUIDv7 has timestamp and sortability
When to Use NanoID
Good for:
- Short, URL-friendly IDs
- Client-side ID generation
- Non-sequential IDs (no ordering needed)
- Custom ID formats
Consider alternatives if:
- You need time-sortable IDs (use ULID or UUIDv7)
- You need to extract timestamps (use ULID or UUIDv7)
- You need distributed coordination (use Snowflake)
- You need UUID compatibility (use UUID)
Common Configurations
API Keys
# Long, alphanumeric
idt gen nanoid --length 32 --alphabet "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"
Short Codes
# 8-character codes (for sharing)
idt gen nanoid --length 8
Numeric IDs
# Numeric only (for phone-friendly codes)
idt gen nanoid --length 6 --alphabet "0123456789"
Specification
- GitHub: https://github.com/ai/nanoid
- Collision calculator: https://zelark.github.io/nano-id-cc/
Snowflake ID
Snowflake IDs are 64-bit identifiers designed by Twitter for distributed systems requiring high-throughput, time-sortable ID generation.
Overview
| Property | Value |
|---|---|
| Bits | 64 |
| Sortable | Yes |
| Timestamp | Yes (millisecond precision) |
| Format | Decimal integer |
| Coordination | Required (machine/datacenter IDs) |
Format
1234567890123456789
|-----------------|
64-bit integer
Bit Structure (Twitter format)
0 | 41 bits timestamp | 5 bits DC | 5 bits Worker | 12 bits sequence
| Field | Bits | Description |
|---|---|---|
| Sign | 1 | Always 0 (positive) |
| Timestamp | 41 | Milliseconds since epoch |
| Datacenter ID | 5 | 0-31 |
| Worker/Machine ID | 5 | 0-31 |
| Sequence | 12 | 0-4095 per millisecond |
Characteristics
High Throughput
- 4096 IDs per millisecond per worker
- 4,096,000 IDs per second per worker
- With 32 workers: ~131 million IDs/second
Time-Sortable
IDs generated later have higher values:
$ idt gen snowflake
1234567890123456789
$ idt gen snowflake
1234567890123456790 # Greater value
Compact
64 bits fits in a single long integer in most languages.
Requires Coordination
Unlike UUIDs, Snowflake IDs require assigning machine/datacenter IDs to avoid collisions.
Generation
# Default Snowflake (Unix epoch, Twitter bit layout)
idt gen snowflake
# With machine ID
idt gen snowflake --machine-id 1
# With datacenter ID
idt gen snowflake --datacenter-id 2
# Both
idt gen snowflake --machine-id 1 --datacenter-id 2
Presets
Use --preset to select a complete Snowflake configuration (bit layout, epoch, and timestamp resolution):
# Twitter (41t + 5dc + 5worker + 12seq, ms, Twitter epoch)
idt gen snowflake --preset twitter
# Discord (same layout as Twitter, Discord epoch)
idt gen snowflake --preset discord
# Instagram (41t + 13shard + 10seq, ms, Instagram epoch)
idt gen snowflake --preset instagram --field shard_id=42
# Sonyflake (39t + 8seq + 16machine, 10ms resolution)
idt gen snowflake --preset sonyflake --machine-id 100
# Mastodon (48t + 16seq, ms, Unix epoch)
idt gen snowflake --preset mastodon
Custom Epochs (backward compatible)
You can also use --epoch for backward compatibility. This uses the Twitter bit layout with the specified epoch:
# Twitter epoch: Nov 4, 2010
idt gen snowflake --epoch twitter
# Discord epoch: Jan 1, 2015
idt gen snowflake --epoch discord
# Custom epoch (milliseconds since Unix epoch)
idt gen snowflake --epoch 1420070400000
Note:
--presetand--epochcannot be used together.
Custom Field Values
Use --field to set arbitrary field values based on the active layout:
# Set shard_id for Instagram layout
idt gen snowflake --preset instagram --field shard_id=42
# Set machine_id for Sonyflake (0-65535)
idt gen snowflake --preset sonyflake --field machine_id=1000
Inspection
$ idt inspect 1234567890123456789
SNOWFLAKE
1234567890123456789
Time (UTC) 2023-01-15T12:34:56.789Z
Local Time (+09:00) 2023-01-15T21:34:56.789+09:00
Datacenter 1
Worker 2
Sequence 789
Hex 112210f47de98115
Base64 ESIQr0fpgRU=
Int 1234567890123456789
Inspecting with Presets
Use --preset to decode with the correct bit layout, epoch, and timestamp resolution:
# Twitter Snowflake
idt inspect --preset twitter 1234567890123456789
# Discord Snowflake
idt inspect --preset discord 1474004412518240339
# Instagram Snowflake (shows shard_id in components)
idt inspect --preset instagram 3852470500357875712
# Sonyflake (10ms resolution)
idt inspect --preset sonyflake 610591162520043520
# Mastodon
idt inspect --preset mastodon 116226149176639488
Inspecting with Custom Epochs (backward compatible)
You can also use --epoch for backward compatibility:
# Discord Snowflake
idt inspect -t snowflake --epoch discord 1474004412518240339
# Twitter Snowflake
idt inspect -t snowflake --epoch twitter 1234567890123456789
# Custom epoch in milliseconds
idt inspect -t snowflake --epoch 1420070400000 1474004412518240339
Without --preset or --epoch, the Unix epoch (0) and Twitter bit layout are used.
Built-in Presets
| Preset | Layout (MSB→LSB) | Epoch (ms) | Timestamp Unit |
|---|---|---|---|
twitter | 41t + 5dc + 5worker + 12seq | 1288834974657 | ms |
discord | 41t + 5dc + 5worker + 12seq | 1420070400000 | ms |
instagram | 41t + 13shard + 10seq | 1314220021721 | ms |
sonyflake | 39t + 8seq + 16machine | 1409529600000 | 10ms |
mastodon | 48t + 16seq | 0 | ms |
Comparison with Other IDs
| Feature | Snowflake | UUID | ULID |
|---|---|---|---|
| Bits | 64 | 128 | 128 |
| Sortable | Yes | No* | Yes |
| Timestamp | Yes | No* | Yes |
| Coordination | Required | No | No |
| Throughput | Very high | High | High |
*UUIDv7 has timestamp and sortability
When to Use Snowflake
Good for:
- High-throughput systems (>100k IDs/second)
- Distributed databases
- Systems needing 64-bit IDs
- Real-time analytics (time-ordered)
Consider alternatives if:
- You can’t coordinate machine IDs (use ULID)
- You need 128-bit IDs (use UUID or ULID)
- You’re generating IDs client-side (use NanoID)
Implementation Notes
Machine ID Assignment
In production, assign machine IDs via:
- Configuration files
- Environment variables
- Service discovery (e.g., ZooKeeper, Consul)
- Database sequences
Clock Skew
Snowflake IDs are sensitive to clock skew:
- Use NTP synchronization
- Some implementations wait for the clock to catch up
- Consider using UUIDv7 if clock skew is a concern
Epoch Selection
Choose an epoch close to your system’s start:
- Maximizes the timestamp range
- Twitter’s epoch gives ~69 years from 2010
- A 2024 epoch would give ~69 years from 2024
Variants
Different systems use different bit layouts, epochs, and timestamp resolutions. All are supported via --preset:
| System | Timestamp | Other Fields | Sequence | Resolution |
|---|---|---|---|---|
| 41 | 5 DC + 5 worker | 12 | ms | |
| Discord | 41 | 5 DC + 5 worker | 12 | ms |
| 41 | 13 shard | 10 | ms | |
| Sonyflake | 39 | 16 machine | 8 | 10ms |
| Mastodon | 48 | — | 16 | ms |
Specification
- Original announcement: https://blog.twitter.com/engineering/en_us/a/2010/announcing-snowflake
- Wikipedia: https://en.wikipedia.org/wiki/Snowflake_ID
Other ID Types
This page covers additional ID types that idt can inspect and work with.
KSUID
K-Sortable Unique Identifier - a 160-bit identifier from Segment.
| Property | Value |
|---|---|
| Bits | 160 |
| Sortable | Yes |
| Timestamp | Yes (second precision) |
| Format | Base62 |
| Length | 27 characters |
Format
0ujsswThIGTUYm2K8FjOOfXtY1K
|-------------------------|
27 Base62 characters
Structure
- Timestamp: 32 bits (seconds since epoch)
- Payload: 128 bits (random)
Characteristics
- Second-level timestamp precision
- 128 bits of randomness
- Base62 encoding (alphanumeric, case-sensitive)
Specification
https://github.com/segmentio/ksuid
MongoDB ObjectId
MongoDB’s default document identifier.
| Property | Value |
|---|---|
| Bits | 96 |
| Sortable | Partial |
| Timestamp | Yes (second precision) |
| Format | Hexadecimal |
| Length | 24 characters |
Format
507f1f77bcf86cd799439011
|----------------------|
24 hex characters
Structure
- Timestamp: 32 bits (Unix seconds)
- Machine identifier: 24 bits
- Process ID: 16 bits
- Counter: 24 bits
Inspection
idt inspect 507f1f77bcf86cd799439011
Specification
https://www.mongodb.com/docs/manual/reference/method/objectid/
TypeID
Type-prefixed, sortable identifiers.
| Property | Value |
|---|---|
| Bits | 128 |
| Sortable | Yes |
| Timestamp | Yes |
| Format | Prefix + Base32 |
Format
user_01h455vb4pex5vsknk084sn02q
|---|-------------------------|
prefix UUIDv7 in Base32
Characteristics
- Type prefix for clarity (e.g.,
user_,order_) - UUIDv7 encoded in Base32
- Type-safe across systems
Specification
https://github.com/jetify-com/typeid
XID
Globally unique, sortable 96-bit identifier.
| Property | Value |
|---|---|
| Bits | 96 |
| Sortable | Yes |
| Timestamp | Yes (second precision) |
| Format | Base32 |
| Length | 20 characters |
Format
9m4e2mr0ui3e8a215n4g
|------------------|
20 Base32 characters
Structure
- Timestamp: 32 bits (Unix seconds)
- Machine ID: 24 bits
- Process ID: 16 bits
- Counter: 24 bits
Characteristics
- Compact (20 characters)
- URL-safe
- Inspired by MongoDB ObjectId
Specification
https://github.com/rs/xid
CUID
Collision-resistant Unique Identifier.
| Property | Value |
|---|---|
| Bits | ~128 |
| Sortable | Partial |
| Timestamp | Yes |
| Format | Custom Base36 |
Format
cjld2cjxh0000qzrmn831i7rn
|-----------------------|
25+ characters
Structure
cprefix- Timestamp
- Counter
- Client fingerprint
- Random block
Specification
https://github.com/paralleldrive/cuid
CUID2
Secure, collision-resistant identifier (CUID successor).
| Property | Value |
|---|---|
| Bits | Variable |
| Sortable | No |
| Timestamp | No |
| Format | Base36 |
| Default length | 24 characters |
Characteristics
- Cryptographically secure
- No timestamp (privacy-focused)
- Configurable length
Specification
https://github.com/paralleldrive/cuid2
TSID
Time-Sorted Unique Identifier.
| Property | Value |
|---|---|
| Bits | 64 |
| Sortable | Yes |
| Timestamp | Yes |
| Format | Base32 or numeric |
Format
0HXNP0P6V80G8 (Base32)
38352658567418876 (numeric)
Structure
- Timestamp: 42 bits
- Node: 10 bits
- Counter: 12 bits
Characteristics
- 64-bit (fits in long integer)
- Similar to Snowflake but with different encoding options
- ~139 years of timestamps
Specification
https://github.com/f4b6a3/tsid-creator
Comparison Table
| Type | Bits | Sortable | Timestamp | Length |
|---|---|---|---|---|
| KSUID | 160 | Yes | Seconds | 27 |
| ObjectId | 96 | Partial | Seconds | 24 |
| TypeID | 128 | Yes | Millis | Variable |
| XID | 96 | Yes | Seconds | 20 |
| CUID | ~128 | Partial | Yes | 25+ |
| CUID2 | Variable | No | No | 24 |
| TSID | 64 | Yes | Millis | 13-17 |
Support Status
These ID types have varying levels of support in idt:
| Type | Generate | Inspect | Convert | Validate |
|---|---|---|---|---|
| KSUID | Planned | Partial | Partial | Yes |
| ObjectId | Planned | Partial | Partial | Yes |
| TypeID | Planned | Partial | Partial | Yes |
| XID | Planned | Partial | Partial | Yes |
| CUID | No | Partial | Partial | Yes |
| CUID2 | No | Partial | Partial | Yes |
| TSID | Planned | Partial | Partial | Yes |
“Partial” means the feature works for basic cases but may not support all options.
Assigned IDs
idt supports validation and inspection of assigned identifiers. Unlike generated IDs (UUID, ULID, etc.), these are not generated by idt — they are issued by external registries, publishers, and standards bodies.
EAN-13
International Article Number — the standard barcode for retail products worldwide.
| Property | Value |
|---|---|
| Length | 13 digits |
| Check Digit | Mod 10 (alternating weights 1, 3) |
| Sortable | No |
| Timestamp | No |
Format
4006381333931
|-----------|X
12 digits check digit
Validation
idt validate -t ean13 4006381333931
# Output: 4006381333931: valid (ean13)
idt inspect 4006381333931
Specification
ISBN-13
International Standard Book Number (current 13-digit format, since 2007).
| Property | Value |
|---|---|
| Length | 13 digits |
| Prefix | 978 or 979 |
| Check Digit | Mod 10 (alternating weights 1, 3) |
| Sortable | No |
| Timestamp | No |
Format
978-0-306-40615-7
|---| |
prefix check digit
ISBN-13 is a subset of EAN-13 with the 978 or 979 prefix.
Conversion
ISBN-13 with prefix 978 can be converted to ISBN-10:
idt inspect 9780306406157
# Components include: isbn10: "0306406152"
Validation
idt validate -t isbn13 978-0-306-40615-7
idt validate -t isbn13 9780306406157
Specification
ISBN-10
International Standard Book Number (legacy 10-character format, pre-2007).
| Property | Value |
|---|---|
| Length | 10 characters (9 digits + check) |
| Check Digit | Mod 11 (weighted), can be 0-9 or X |
| Sortable | No |
| Timestamp | No |
Format
0-306-40615-2
|---------|X
9 digits check digit (0-9 or X)
The check digit X represents the value 10 in the Mod 11 algorithm.
Conversion
Every ISBN-10 can be converted to ISBN-13 by prepending 978 and recalculating the check digit:
idt inspect 0306406152
# Components include: isbn13: "9780306406157"
Validation
idt validate -t isbn10 0306406152
idt validate -t isbn10 080442957X # X as check digit
idt validate -t isbn10 0-306-40615-2 # hyphens are stripped
Specification
ISIN
International Securities Identification Number — uniquely identifies securities (stocks, bonds, derivatives).
| Property | Value |
|---|---|
| Length | 12 characters |
| Structure | 2-letter country code + 9 alphanumeric + 1 check digit |
| Check Digit | Luhn algorithm (letters converted: A=10, B=11, …, Z=35) |
| Sortable | No |
| Timestamp | No |
Format
US0378331005
|--|-------|X
CC NSIN check digit
- CC: ISO 3166-1 alpha-2 country code
- NSIN: National Securities Identifying Number (9 alphanumeric characters)
- Check digit: Luhn algorithm applied after converting letters to numbers
Validation
idt validate -t isin US0378331005 # Apple Inc.
idt validate -t isin GB0002634946 # BAE Systems
idt validate -t isin AU0000XVGZA3 # Australian security
Inspection
idt inspect US0378331005
# Components: country_code: "US", nsin: "037833100", check_digit: "5"
Specification
EAN-8
8-digit barcode for small items where EAN-13 is too large.
| Property | Value |
|---|---|
| Length | 8 digits |
| Check Digit | Mod 10 (alternating weights 1, 3) |
| Sortable | No |
| Timestamp | No |
Format
96385074
|------|X
7 digits check digit
Validation
idt validate -t ean8 96385074
# Output: 96385074: valid (ean8)
Specification
UPC-A
Universal Product Code — the standard 12-digit barcode used in North America.
| Property | Value |
|---|---|
| Length | 12 digits |
| Check Digit | Mod 10 (alternating weights 1, 3) |
| Sortable | No |
| Timestamp | No |
Format
036000291452
|----------|X
11 digits check digit
Conversion
UPC-A can be converted to EAN-13 by prepending a leading zero:
idt inspect 036000291452
# Components include: ean13: "0036000291452"
Validation
idt validate -t upca 036000291452
Specification
ISSN
International Standard Serial Number — identifies serial publications (journals, magazines, newspapers).
| Property | Value |
|---|---|
| Length | 8 characters |
| Format | XXXX-XXXX |
| Check Digit | Mod 11 (weighted), can be 0-9 or X |
| Sortable | No |
| Timestamp | No |
Format
0378-5955
|------|X
7 digits check digit (0-9 or X)
Validation
idt validate -t issn 0378-5955
idt validate -t issn 03785955 # without hyphen
Specification
ISMN
International Standard Music Number — identifies printed music publications.
| Property | Value |
|---|---|
| Length | 13 digits |
| Prefix | 979-0 |
| Check Digit | Mod 10 (alternating weights 1, 3) |
| Sortable | No |
| Timestamp | No |
Format
979-0-060-11561-5
|---| |
prefix check digit
ISMN is a subset of EAN-13 with the 979-0 prefix.
Validation
idt validate -t ismn 979-0-060-11561-5
idt validate -t ismn 9790060115615
Specification
ISNI
International Standard Name Identifier — uniquely identifies contributors to creative works.
| Property | Value |
|---|---|
| Length | 16 characters |
| Format | XXXX XXXX XXXX XXXX |
| Check Digit | ISO 7064 MOD 11-2 (last char can be 0-9 or X) |
| Sortable | No |
| Timestamp | No |
Format
0000 0001 2103 2683
|--- ---- ---- ---|X
15 digits check digit
Validation
idt validate -t isni "0000 0001 2103 2683"
idt validate -t isni 0000000121032683
Specification
GTIN-14
Global Trade Item Number — identifies trade items at various packaging levels.
| Property | Value |
|---|---|
| Length | 14 digits |
| Check Digit | Mod 10 (alternating weights 1, 3) |
| Sortable | No |
| Timestamp | No |
Format
10614141000415
X|-----------|X
PI check digit
- PI: Packaging indicator (first digit)
Validation
idt validate -t gtin14 10614141000415
Specification
ASIN
Amazon Standard Identification Number — Amazon’s proprietary product identifier.
| Property | Value |
|---|---|
| Length | 10 characters |
| Characters | Alphanumeric (uppercase) |
| Check Digit | None (format validation only) |
| Sortable | No |
| Timestamp | No |
Format
B08N5WRWNW
ASINs starting with B are Amazon-assigned. ASINs starting with a digit are typically ISBN-10 based.
Validation
idt validate -t asin B08N5WRWNW
Comparison
| Type | Length | Characters | Check Algorithm | Use Case |
|---|---|---|---|---|
| EAN-13 | 13 | Digits | Mod 10 (1,3) | Retail barcodes |
| EAN-8 | 8 | Digits | Mod 10 (1,3) | Small item barcodes |
| UPC-A | 12 | Digits | Mod 10 (1,3) | North American products |
| ISBN-13 | 13 | Digits | Mod 10 (1,3) | Books |
| ISBN-10 | 10 | Digits + X | Mod 11 | Books (legacy) |
| ISSN | 8 | Digits + X | Mod 11 | Serial publications |
| ISMN | 13 | Digits | Mod 10 (1,3) | Printed music |
| ISNI | 16 | Digits + X | ISO 7064 MOD 11-2 | Name identifiers |
| ISIN | 12 | Alphanumeric | Luhn | Securities |
| GTIN-14 | 14 | Digits | Mod 10 (1,3) | Trade items |
| ASIN | 10 | Alphanumeric | None | Amazon products |
Support Status
| Type | Generate | Inspect | Convert | Validate |
|---|---|---|---|---|
| EAN-13 | No | Yes | Yes | Yes |
| EAN-8 | No | Yes | Yes | Yes |
| UPC-A | No | Yes | Yes | Yes |
| ISBN-13 | No | Yes | Yes | Yes |
| ISBN-10 | No | Yes | Yes | Yes |
| ISSN | No | Yes | Yes | Yes |
| ISMN | No | Yes | Yes | Yes |
| ISNI | No | Yes | Yes | Yes |
| ISIN | No | Yes | Yes | Yes |
| GTIN-14 | No | Yes | Yes | Yes |
| ASIN | No | Yes | Yes | Yes |
Examples Overview
This section provides practical examples for common idt use cases.
Quick Examples
Generate and Use
# Generate a UUID and store it
ID=$(idt gen uuidv7 --no-newline)
echo "Created resource with ID: $ID"
# Generate and insert into database
idt gen uuid | xargs -I {} psql -c "INSERT INTO items (id) VALUES ('{}')"
Inspect Unknown IDs
# What type of ID is this?
idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
# When was it created?
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --json | jq '.timestamp_iso'
Batch Operations
# Generate 1000 UUIDs to file
idt gen uuid -n 1000 -o uuids.txt
# Validate all IDs in a file
cat ids.txt | idt validate
# Convert a list of IDs
cat uuids.txt | idt convert -f base64
Example Categories
- Generating IDs - ID generation patterns
- Inspecting IDs - Analyzing and decoding IDs
- Converting Formats - Format transformation
- Shell Scripting - Integration with shell scripts
- JSON Output - Machine-readable output
Common Patterns
Database Primary Keys
# Generate sortable primary key
idt gen uuidv7
# Generate for existing UUID column
idt gen uuid
API Tokens
# Long, secure token
idt gen nanoid --length 32
# URL-safe token
idt gen nanoid --alphabet "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"
Debugging
# Decode ID from logs
idt inspect "01ARZ3NDEKTSV4RRFFQ69G5FAV"
# Compare two IDs for ordering
idt compare "$OLD_ID" "$NEW_ID"
# Sort IDs from logs by creation time
cat log_ids.txt | idt sort --show-time
Data Migration
# Convert UUID format for different system
idt convert "550e8400-e29b-41d4-a716-446655440000" -f base64
# Validate IDs before import
cat export.csv | cut -d, -f1 | idt validate
Generating IDs
Examples for generating various types of identifiers.
Basic Generation
UUIDs
# Random UUID (v4) - most common
idt gen uuid
# Time-sortable UUID (v7) - recommended for new projects
idt gen uuidv7
# Timestamp-based UUID (v1)
idt gen uuidv1
# Reordered timestamp UUID (v6)
idt gen uuidv6
Other Formats
# ULID - compact, sortable
idt gen ulid
# NanoID - short, URL-friendly
idt gen nanoid
# Snowflake - 64-bit distributed ID
idt gen snowflake
Batch Generation
# Generate 10 UUIDs
idt gen uuid -n 10
# Generate 1000 ULIDs
idt gen ulid -n 1000
# Generate to file
idt gen uuidv7 -n 10000 -o ids.txt
Customization
NanoID Options
# Custom length (default is 21)
idt gen nanoid --length 16
idt gen nanoid --length 32
# Custom alphabet
idt gen nanoid --alphabet "0123456789" # Numeric only
idt gen nanoid --alphabet "0123456789abcdef" # Hex
idt gen nanoid --alphabet "ABCDEFGHIJKLMNOP" # Uppercase only
# Combined
idt gen nanoid --length 8 --alphabet "0123456789"
Snowflake Options
# Use presets for different services
idt gen snowflake --preset twitter
idt gen snowflake --preset discord
idt gen snowflake --preset instagram --field shard_id=42
idt gen snowflake --preset sonyflake --machine-id 100
idt gen snowflake --preset mastodon
# With machine/datacenter IDs
idt gen snowflake --machine-id 1 --datacenter-id 2
# Named epochs (backward compatible)
idt gen snowflake --epoch twitter
idt gen snowflake --epoch discord
idt gen snowflake --epoch 1420070400000
Output Formats
Different Encodings
# Generate as hex (no dashes)
idt gen uuid -f hex
# Generate as Base64
idt gen uuidv7 -f base64
# Generate as integer
idt gen ulid -f int
JSON Output
# Single ID as JSON object
idt gen uuid --json
# {"id":"550e8400-e29b-41d4-a716-446655440000"}
# Multiple IDs as JSON array
idt gen uuid -n 5 --json
# ["550e8400-...","6ba7b810-...",...]
# Pretty-printed
idt gen uuid --json --pretty
No Trailing Newline
# Useful for variable assignment
ID=$(idt gen uuid --no-newline)
# For inline use
echo "ID: $(idt gen uuid --no-newline)"
Practical Examples
Template Output
# Wrap IDs in a SQL statement
idt gen uuidv7 -T 'INSERT INTO users (id) VALUES ("{}");'
# Generate JSON fixtures
idt gen uuidv7 -n 5 -T '{"id": "{}"}'
# Combine with encoding format
idt gen uuidv7 -f hex -T 'id={}'
Database Seeding
# Generate SQL inserts directly with --template
idt gen uuidv7 -n 100 -T "INSERT INTO users (id, name) VALUES ('{}', 'test');"
# Or with shell logic for dynamic values
for i in {1..100}; do
ID=$(idt gen uuidv7 --no-newline)
echo "INSERT INTO users (id, name) VALUES ('$ID', 'User $i');"
done
API Key Generation
# Generate secure API keys
idt gen nanoid --length 32 -n 10
# With custom prefix
for i in {1..5}; do
KEY=$(idt gen nanoid --length 24 --no-newline)
echo "sk_live_$KEY"
done
File Naming
# Generate unique filename
FILENAME="backup_$(idt gen nanoid --length 8 --no-newline).tar.gz"
tar -czf "$FILENAME" /data
# With timestamp from ULID
ULID=$(idt gen ulid --no-newline)
mv upload.pdf "document_${ULID}.pdf"
Distributed System IDs
# Server 1 (machine-id 1)
idt gen snowflake --machine-id 1
# Server 2 (machine-id 2)
idt gen snowflake --machine-id 2
# Different datacenters
idt gen snowflake --machine-id 1 --datacenter-id 1 # DC 1
idt gen snowflake --machine-id 1 --datacenter-id 2 # DC 2
Verification Codes
# 6-digit numeric code
idt gen nanoid --length 6 --alphabet "0123456789"
# Alphanumeric confirmation code
idt gen nanoid --length 8 --alphabet "ABCDEFGHJKLMNPQRSTUVWXYZ23456789"
Performance
Bulk Generation
# Generate 100,000 IDs efficiently
time idt gen uuid -n 100000 > /dev/null
# Write to file
idt gen uuidv7 -n 1000000 -o million_ids.txt
Parallel Generation
# Use parallel for very large batches
seq 10 | parallel "idt gen uuid -n 100000" > all_ids.txt
Inspecting IDs
Examples for analyzing and decoding identifiers to extract embedded information.
Basic Inspection
Auto-Detection
idt automatically detects the ID type:
# UUID
idt inspect 550e8400-e29b-41d4-a716-446655440000
# ULID
idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
# Snowflake
idt inspect 1234567890123456789
With Type Hint
Force interpretation as a specific type:
# Parse as UUID (even without dashes)
idt inspect -t uuid 550e8400e29b41d4a716446655440000
# Parse as ULID
idt inspect -t ulid 01ARZ3NDEKTSV4RRFFQ69G5FAV
Extracting Information
Timestamps
# Get creation time from UUIDv7
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469
# Output includes:
# Time (UTC) 2026-01-28T13:57:47.416Z
# Local Time (+09:00) 2026-01-28T22:57:47.416+09:00
Using JSON to extract specific fields:
# Get timestamp as ISO string (UTC)
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --json | jq -r '.timestamp_iso'
# Get timestamp in local timezone
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --json | jq -r '.timestamp_local_iso'
# Get timestamp as milliseconds
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --json | jq '.timestamp'
UUID Version and Variant
# Inspect UUID to see version
idt inspect 550e8400-e29b-41d4-a716-446655440000
# Output includes:
# Version 4
# Variant RFC4122
Multiple Encodings
Every inspection shows the ID in multiple formats:
idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV
# Output includes:
# Hex 01563e3ab5d3d6764c61efb99302bd5b
# Base64 AVY+OrXT1nZMYe+5kwK9Ww==
# Int 1777027686520646174104517696511196507
Batch Inspection
Multiple Arguments
# Inspect multiple IDs
idt inspect id1 id2 id3
From File
# Inspect all IDs in a file
cat ids.txt | idt inspect
# Only valid IDs
cat ids.txt | idt inspect 2>/dev/null
Pipeline
# Generate and immediately inspect
idt gen uuidv7 | idt inspect
# Inspect IDs from another command
grep -o '[0-9a-f-]\{36\}' logfile.log | idt inspect
JSON Output
Single ID
idt inspect 550e8400-e29b-41d4-a716-446655440000 --json --pretty
Output:
{
"id_type": "uuidv4",
"canonical": "550e8400-e29b-41d4-a716-446655440000",
"version": "4",
"variant": "RFC4122",
"random_bits": 122,
"encodings": {
"hex": "550e8400e29b41d4a716446655440000",
"base64": "VQ6EAOKbQdSnFkRmVUQAAA==",
"int": "113059749145936325402354257176981405696"
}
}
Extract Specific Fields
# Get ID type
idt inspect "$ID" --json | jq -r '.id_type'
# Get all encodings
idt inspect "$ID" --json | jq '.encodings'
# Get hex representation
idt inspect "$ID" --json | jq -r '.encodings.hex'
Practical Examples
Debug Logging
# Decode ID from error logs
grep "failed.*id:" error.log | awk '{print $NF}' | idt inspect
# Find when an event occurred (UTC)
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --json | jq -r '.timestamp_iso'
# Output: 2026-01-28T13:57:47.416Z
# Find when an event occurred (local time)
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --json | jq -r '.timestamp_local_iso'
# Output: 2026-01-28T22:57:47.416+09:00
Data Analysis
# Analyze IDs from database export
psql -c "SELECT id FROM events" -t | idt inspect --json | jq -r '.timestamp_iso' | sort
# Group by ID type
cat mixed_ids.txt | while read id; do
TYPE=$(idt inspect "$id" --json 2>/dev/null | jq -r '.id_type')
echo "$TYPE: $id"
done
Verify ID Properties
# Check if ID is time-sortable
TYPE=$(idt inspect "$ID" --json | jq -r '.id_type')
case "$TYPE" in
uuidv7|ulid|snowflake) echo "Time-sortable" ;;
*) echo "Not time-sortable" ;;
esac
# Check if ID has timestamp
if idt inspect "$ID" --json | jq -e '.timestamp' > /dev/null 2>&1; then
echo "Has timestamp"
else
echo "No timestamp"
fi
Convert Between Systems
# Get UUID-compatible hex for ULID
idt inspect 01ARZ3NDEKTSV4RRFFQ69G5FAV --json | jq -r '.encodings.hex'
# Can be used as: INSERT INTO uuid_col VALUES('01563e3ab5d3d6764c61efb99302bd5b')
Error Handling
Invalid IDs
# Invalid ID shows error
idt inspect "not-a-valid-id"
# Error parsing 'not-a-valid-id': Not a recognized ID format
# Quiet mode for scripts
if idt inspect -q "$ID" 2>/dev/null; then
echo "Valid"
else
echo "Invalid"
fi
Ambiguous IDs
Some strings could be multiple ID types:
# Provide type hint to disambiguate
idt inspect -t uuid "$AMBIGUOUS_ID"
Snowflake Presets
Use --preset to decode Snowflake IDs with the correct bit layout, epoch, and timestamp resolution:
# Decode with preset (recommended)
idt inspect --preset twitter 1234567890123456789
idt inspect --preset discord 1474004412518240339
idt inspect --preset instagram 3852470500357875712 # Shows shard_id
idt inspect --preset sonyflake 610591162520043520 # 10ms resolution
idt inspect --preset mastodon 116226149176639488
# Extract timestamp from a Discord Snowflake via JSON
idt inspect --preset discord 1474004412518240339 --json | jq -r '.timestamp_iso'
Backward-compatible –epoch flag
# Decode with epoch (uses Twitter bit layout)
idt inspect -t snowflake --epoch discord 1474004412518240339
idt inspect -t snowflake --epoch twitter 1234567890123456789
idt inspect -t snowflake --epoch 1420070400000 1474004412518240339
Converting Formats
Examples for converting IDs between different encoding formats.
Basic Conversions
To Hexadecimal
# UUID to hex (removes dashes)
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex
# Output: 550e8400e29b41d4a716446655440000
# ULID to hex
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f hex
# Output: 01563e3ab5d3d6764c61efb99302bd5b
To Base64
# Standard Base64
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
# Output: VQ6EAOKbQdSnFkRmVUQAAA==
# URL-safe Base64 (no padding)
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64url
# Output: VQ6EAOKbQdSnFkRmVUQAAA
To Base58
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base58
# Output: 6K8FVbLqP4V8nDqTJNXH6k
To Integer
idt convert 550e8400-e29b-41d4-a716-446655440000 -f int
# Output: 113059749145936325402354257176981405696
All Formats
ID="550e8400-e29b-41d4-a716-446655440000"
# Each encoding format
idt convert "$ID" -f canonical # Original format
idt convert "$ID" -f hex # Hexadecimal
idt convert "$ID" -f base32 # Base32
idt convert "$ID" -f base58 # Base58
idt convert "$ID" -f base64 # Base64
idt convert "$ID" -f base64url # URL-safe Base64
idt convert "$ID" -f bits # Binary string
idt convert "$ID" -f int # Integer
idt convert "$ID" -f bytes # Space-separated hex bytes
Case Transformation
Uppercase
# Uppercase hex
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex -U
# Output: 550E8400E29B41D4A716446655440000
Lowercase
# Lowercase (normalize)
idt convert 550E8400-E29B-41D4-A716-446655440000 -f hex -L
# Output: 550e8400e29b41d4a716446655440000
Batch Conversion
Multiple IDs
# Convert multiple IDs
idt convert id1 id2 id3 -f base64
From File
# Convert all IDs in a file
cat uuids.txt | idt convert -f hex
# Save converted IDs
cat uuids.txt | idt convert -f base64 > encoded.txt
Pipeline
# Generate and convert
idt gen uuid | idt convert -f base64
# Convert output from another command
grep -o '[0-9a-f-]\{36\}' logfile.log | idt convert -f hex
Practical Examples
Database Compatibility
# PostgreSQL bytea format
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex
# Use as: INSERT INTO table (id) VALUES (decode('550e8400...', 'hex'))
# Binary storage
idt convert 550e8400-e29b-41d4-a716-446655440000 -f bytes
# Output: 55 0e 84 00 e2 9b 41 d4 a7 16 44 66 55 44 00 00
URL Encoding
# URL-safe encoding for API calls
ID=$(idt gen uuidv7 --no-newline)
ENCODED=$(echo "$ID" | idt convert -f base64url)
curl "https://api.example.com/item/$ENCODED"
Cross-System Integration
# System A uses UUIDs with dashes
UUID="550e8400-e29b-41d4-a716-446655440000"
# System B uses hex without dashes
HEX=$(idt convert "$UUID" -f hex)
# 550e8400e29b41d4a716446655440000
# System C uses Base64
B64=$(idt convert "$UUID" -f base64)
# VQ6EAOKbQdSnFkRmVUQAAA==
Data Migration
# Convert exported IDs for import
cat export.csv | while IFS=, read id name; do
NEW_ID=$(idt convert "$id" -f hex)
echo "$NEW_ID,$name"
done > import.csv
Compact Storage
# Store IDs more compactly
# UUID: 36 chars -> Base64: 24 chars -> Base58: ~22 chars
# Original
550e8400-e29b-41d4-a716-446655440000 # 36 chars
# Base64
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
VQ6EAOKbQdSnFkRmVUQAAA== # 24 chars
# Base58
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base58
6K8FVbLqP4V8nDqTJNXH6k # 22 chars
Binary Analysis
# View binary representation
idt convert 550e8400-e29b-41d4-a716-446655440000 -f bits
# Output: 01010101000011101000010000000000...
# View byte-by-byte
idt convert 550e8400-e29b-41d4-a716-446655440000 -f bytes
# Output: 55 0e 84 00 e2 9b 41 d4 a7 16 44 66 55 44 00 00
JSON Output
# Get converted value as JSON
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex --json
# Output: "550e8400e29b41d4a716446655440000"
# Multiple IDs
idt convert id1 id2 -f base64 --json
# Output: ["VQ6E...","6ba7..."]
Type Hints
When auto-detection fails:
# Interpret as UUID
idt convert -t uuid 550e8400e29b41d4a716446655440000 -f canonical
# Output: 550e8400-e29b-41d4-a716-446655440000
Shell Scripting
Examples for integrating idt into shell scripts and Unix pipelines.
Variable Assignment
Basic Assignment
# Generate and store ID
ID=$(idt gen uuid)
echo "Generated ID: $ID"
# Use --no-newline for cleaner assignment
ID=$(idt gen uuidv7 --no-newline)
Multiple IDs
# Store in array (bash)
mapfile -t IDS < <(idt gen uuid -n 10)
echo "First ID: ${IDS[0]}"
echo "Total: ${#IDS[@]}"
Conditional Logic
Validation
# Check if ID is valid
if idt validate -q "$ID" 2>/dev/null; then
echo "Valid ID: $ID"
else
echo "Invalid ID: $ID"
exit 1
fi
Type Checking
# Check ID type
TYPE=$(idt inspect "$ID" --json 2>/dev/null | jq -r '.id_type')
case "$TYPE" in
uuidv7|ulid)
echo "Time-sortable ID"
;;
uuidv4)
echo "Random UUID"
;;
*)
echo "Other type: $TYPE"
;;
esac
Pipelines
Generate and Process
# Generate, convert, and use
idt gen uuidv7 | idt convert -f base64 | xargs echo "Encoded:"
# Generate multiple and filter
idt gen uuid -n 100 | grep '^[0-4]' # IDs starting with 0-4
Process Files
# Validate IDs from file
cat ids.txt | idt validate
# Convert all IDs in file
cat uuids.txt | idt convert -f hex > hex_ids.txt
# Inspect and extract timestamps
cat ids.txt | idt inspect --json | jq -r '.timestamp_iso'
Sort by Timestamp
# Sort IDs from a file by creation time
cat ids.txt | idt sort --show-time
# Find the most recent ID
cat ids.txt | idt sort --reverse | head -1
# Generate and sort with timestamps
idt gen ulid -n 10 | idt sort --show-time --reverse
Chain Commands
# Generate -> Inspect -> Extract
idt gen uuidv7 | idt inspect --json | jq -r '.timestamp_iso'
# Complex pipeline
idt gen ulid -n 1000 | \
idt inspect --json | \
jq -r '.encodings.hex' | \
sort | \
head -10
Loops
Process Multiple IDs
# Process each ID individually
while read -r id; do
echo "Processing: $id"
idt inspect "$id" --json | jq -r '.id_type'
done < ids.txt
Generate with Custom Logic
# Generate IDs with prefixes
for type in user order item; do
ID=$(idt gen nanoid --length 16 --no-newline)
echo "${type}_${ID}"
done
Batch Processing
# Use --template for simple formatting (no shell loop needed)
idt gen uuid -n 1000 -T "INSERT INTO table VALUES ('{}');" | psql mydb
# Or use a loop for more complex logic
idt gen uuid -n 1000 | while read -r id; do
echo "INSERT INTO table VALUES ('$id');"
done | psql mydb
Error Handling
Check Exit Codes
# Validate with error handling
if ! idt validate -q "$ID" 2>/dev/null; then
echo "Error: Invalid ID '$ID'" >&2
exit 1
fi
Capture Errors
# Capture both output and errors
RESULT=$(idt inspect "$ID" 2>&1)
if [ $? -eq 0 ]; then
echo "Success: $RESULT"
else
echo "Error: $RESULT" >&2
fi
Continue on Error
# Process all, report errors
cat ids.txt | while read -r id; do
if idt validate -q "$id" 2>/dev/null; then
echo "$id" >> valid.txt
else
echo "$id" >> invalid.txt
fi
done
Practical Scripts
Database Seeding Script
#!/bin/bash
# seed_database.sh - Generate test data with unique IDs
COUNT=${1:-100}
TABLE=${2:-users}
echo "Seeding $TABLE with $COUNT records..."
idt gen uuidv7 -n "$COUNT" | while read -r id; do
NAME="User_$(idt gen nanoid --length 8 --no-newline)"
echo "INSERT INTO $TABLE (id, name) VALUES ('$id', '$NAME');"
done | psql mydb
echo "Done!"
ID Migration Script
#!/bin/bash
# migrate_ids.sh - Convert IDs between formats
INPUT_FILE=$1
OUTPUT_FORMAT=${2:-base64}
if [ -z "$INPUT_FILE" ]; then
echo "Usage: $0 <input_file> [format]"
exit 1
fi
cat "$INPUT_FILE" | while read -r id; do
CONVERTED=$(idt convert "$id" -f "$OUTPUT_FORMAT" 2>/dev/null)
if [ -n "$CONVERTED" ]; then
echo "$CONVERTED"
else
echo "# Failed: $id" >&2
fi
done
ID Validation Script
#!/bin/bash
# validate_export.sh - Validate IDs in CSV export
FILE=$1
COLUMN=${2:-1}
if [ -z "$FILE" ]; then
echo "Usage: $0 <csv_file> [column_number]"
exit 1
fi
TOTAL=0
VALID=0
INVALID=0
tail -n +2 "$FILE" | cut -d',' -f"$COLUMN" | while read -r id; do
((TOTAL++))
if idt validate -q "$id" 2>/dev/null; then
((VALID++))
else
((INVALID++))
echo "Invalid at line $TOTAL: $id" >&2
fi
done
echo "Total: $TOTAL, Valid: $VALID, Invalid: $INVALID"
Timestamp Extraction Script
#!/bin/bash
# extract_timestamps.sh - Extract creation times from IDs
while read -r id; do
TIMESTAMP=$(idt inspect "$id" --json 2>/dev/null | jq -r '.timestamp_iso // "N/A"')
echo "$id -> $TIMESTAMP"
done
Integration with Other Tools
With jq
# Extract specific fields
idt inspect "$ID" --json | jq '{type: .id_type, time: .timestamp_iso}'
# Filter by type
idt gen uuid -n 10 --json | jq '.[]'
With xargs
# Process IDs in parallel
cat ids.txt | xargs -P 4 -I {} sh -c 'idt inspect "{}" --json'
With awk
# Combine with awk processing
idt gen uuid -n 100 | awk '{print NR": "$0}'
With parallel
# High-performance parallel processing
cat large_ids.txt | parallel -j 8 'idt inspect {} --json'
Structured Output (JSON, YAML, TOML)
Examples for using idt’s structured output formats for machine-readable data processing.
Enabling Structured Output
Using --output / -o
# JSON output
idt gen uuid --output json
idt inspect "$ID" --output yaml
idt validate "$ID" --output toml
# Short form
idt gen uuid -o json
idt inspect "$ID" -o yaml
JSON Shorthand (--json / -j)
# --json and -j are shortcuts for --output json
idt gen uuid --json
idt gen uuid -j
idt inspect "$ID" --json
idt validate "$ID" --json
idt compare "$ID1" "$ID2" --json
idt info --json
Pretty-Printed JSON
# Add --pretty for formatted JSON output
idt inspect "$ID" --json --pretty
idt inspect "$ID" --output json --pretty
Command Outputs
gen Command
# Single ID
idt gen uuid --json
# {"id":"550e8400-e29b-41d4-a716-446655440000"}
# Multiple IDs
idt gen uuid -n 3 --json
# ["550e8400-...","6ba7b810-...","7c9e6679-..."]
inspect Command
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --json --pretty
Output:
{
"id_type": "uuidv7",
"canonical": "019c04e5-6118-7b22-95cb-a10e84dad469",
"timestamp": 1706450267416,
"timestamp_iso": "2026-01-28T13:57:47.416Z",
"timestamp_local_iso": "2026-01-28T22:57:47.416+09:00",
"version": "7",
"variant": "RFC4122",
"random_bits": 62,
"encodings": {
"hex": "019c04e561187b2295cba10e84dad469",
"base64": "AZwE5WEYeyKVy6EOhNrUaQ==",
"int": "2139325608653621017571381452845274217"
}
}
validate Command
idt validate 550e8400-e29b-41d4-a716-446655440000 --json
Output:
{
"input": "550e8400-e29b-41d4-a716-446655440000",
"valid": true,
"id_type": "uuidv4"
}
Invalid ID:
{
"input": "not-valid",
"valid": false,
"error": "Not a recognized ID format"
}
compare Command
idt compare "$ID1" "$ID2" --json --pretty
Output:
{
"id1": "019c04e5-6118-7b22-95cb-a10e84dad469",
"id2": "019c04e5-6119-7000-8000-000000000000",
"type1": "uuidv7",
"type2": "uuidv7",
"binary_order": "less",
"lexicographic_order": "less",
"chronological_order": "less",
"time_diff_ms": 1000,
"timestamp1": 1706450267416,
"timestamp2": 1706450268416
}
info Command
idt info uuidv7 --json --pretty
Output:
{
"name": "uuidv7",
"description": "Unix timestamp + random",
"has_timestamp": true,
"is_sortable": true,
"bit_length": 128,
"example": "019c04e5-6118-7b22-95cb-a10e84dad469",
"spec_url": "https://datatracker.ietf.org/doc/html/rfc9562",
"notes": [
"Recommended for new applications needing sortable UUIDs",
"Unix timestamp in milliseconds",
"Compatible with UUID infrastructure"
]
}
YAML Output
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --output yaml
Output:
id_type: uuidv7
canonical: 019c04e5-6118-7b22-95cb-a10e84dad469
valid: true
version: '7'
variant: RFC4122
random_bits: 62
encodings:
hex: 019c04e561187b2295cba10e84dad469
base64: AZwE5WEYeyKVy6EOhNrUaQ==
int: '2139325608653621017571381452845274217'
TOML Output
idt inspect 019c04e5-6118-7b22-95cb-a10e84dad469 --output toml
Output:
id_type = "uuidv7"
canonical = "019c04e5-6118-7b22-95cb-a10e84dad469"
valid = true
version = "7"
variant = "RFC4122"
random_bits = 62
[encodings]
hex = "019c04e561187b2295cba10e84dad469"
base64 = "AZwE5WEYeyKVy6EOhNrUaQ=="
int = "2139325608653621017571381452845274217"
Processing with jq
Extract Fields
# Get ID type
idt inspect "$ID" --json | jq -r '.id_type'
# Get timestamp
idt inspect "$ID" --json | jq -r '.timestamp_iso'
# Get specific encoding
idt inspect "$ID" --json | jq -r '.encodings.hex'
Filter and Transform
# Get only sortable types
idt info --json | jq '[.[] | select(.is_sortable)]'
# Extract names of types with timestamps
idt info --json | jq -r '.[] | select(.has_timestamp) | .name'
# Create custom object
idt inspect "$ID" --json | jq '{id: .canonical, created: .timestamp_iso}'
Batch Processing
# Process multiple IDs
cat ids.txt | while read id; do
idt inspect "$id" --json
done | jq -s '.' # Combine into array
# Extract timestamps from multiple IDs
cat ids.txt | while read id; do
idt inspect "$id" --json
done | jq -r '.timestamp_iso'
Integration Examples
Store in Database
# Generate structured data for insertion
idt gen uuidv7 --json | jq -r '
"INSERT INTO ids (id, created_at) VALUES (\(.id), NOW());"
'
API Integration
# Generate ID and create JSON payload
ID=$(idt gen uuidv7 --no-newline)
PAYLOAD=$(jq -n --arg id "$ID" '{"resource_id": $id, "type": "new"}')
curl -X POST -d "$PAYLOAD" https://api.example.com/resources
Logging
# Structured logging
idt inspect "$ID" --json | jq -c '{
event: "id_inspected",
id_type: .id_type,
timestamp: .timestamp_iso
}'
Configuration Files
# Generate config with new IDs
cat config.template.json | jq --arg id "$(idt gen uuidv7 --no-newline)" '
.session_id = $id
'
Converting Output
To CSV
# Convert JSON output to CSV
idt info --json | jq -r '
["name","has_timestamp","is_sortable","bit_length"],
(.[] | [.name, .has_timestamp, .is_sortable, .bit_length])
| @csv
'
To TSV
# Convert to tab-separated
idt info --json | jq -r '.[] | [.name, .description] | @tsv'
To Environment Variables
# Export as env vars
eval $(idt inspect "$ID" --json | jq -r '
"export ID_TYPE=\(.id_type)",
"export ID_TIMESTAMP=\(.timestamp_iso // "none")"
')
Error Handling
Check for Errors
# Check if valid JSON was returned
RESULT=$(idt inspect "$ID" --json 2>&1)
if echo "$RESULT" | jq -e . >/dev/null 2>&1; then
echo "Valid JSON: $RESULT"
else
echo "Error: $RESULT" >&2
fi
Handle Missing Fields
# Use // for default values
idt inspect "$ID" --json | jq -r '.timestamp_iso // "No timestamp"'
Performance Tips
Avoid Pretty Print in Pipelines
# Fast (compact JSON)
idt gen uuid -n 1000 --json | jq '.[]'
# Slower (pretty printed)
idt gen uuid -n 1000 --json --pretty | jq '.[]'
Use jq Streaming for Large Data
# Stream processing for large datasets
idt gen uuid -n 10000 --json | jq -c '.[]'
Encoding Formats
idt supports various encoding formats for converting and displaying IDs.
Available Formats
| Format | Description | Example (128-bit UUID) |
|---|---|---|
canonical | Original/standard format | 550e8400-e29b-41d4-a716-446655440000 |
hex | Hexadecimal (lowercase) | 550e8400e29b41d4a716446655440000 |
base32 | RFC 4648 Base32 | KUHIBAASSNE5JJYWIRDFKRAAAA |
base58 | Bitcoin-style Base58 | 6K8FVbLqP4V8nDqTJNXH6k |
base64 | Standard Base64 | VQ6EAOKbQdSnFkRmVUQAAA== |
base64url | URL-safe Base64 | VQ6EAOKbQdSnFkRmVUQAAA |
bits | Binary string | 01010101000011101000... |
int | Integer representation | 113059749145936325402354257176981405696 |
bytes | Space-separated hex bytes | 55 0e 84 00 e2 9b 41 d4... |
Format Details
Canonical
The standard format for each ID type:
- UUID:
xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx(36 characters) - ULID: 26 Crockford Base32 characters
- NanoID: Variable length (default 21 characters)
- Snowflake: Decimal integer
idt convert "$ID" -f canonical
Hexadecimal (hex)
Raw bytes as hexadecimal characters (lowercase).
- Length: 2 characters per byte
- Characters:
0-9,a-f - Use case: Database storage, binary comparison
idt convert 550e8400-e29b-41d4-a716-446655440000 -f hex
# Output: 550e8400e29b41d4a716446655440000
Base32
RFC 4648 Base32 encoding (without padding).
- Characters:
A-Z,2-7 - Use case: Case-insensitive encoding, DNS-safe
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base32
# Output: KUHIBAASSNE5JJYWIRDFKRAAAA
Base58
Bitcoin-style Base58 encoding (excludes 0, O, I, l).
- Characters:
1-9,A-H,J-N,P-Z,a-k,m-z - Use case: User-friendly, avoids ambiguous characters
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base58
# Output: 6K8FVbLqP4V8nDqTJNXH6k
Base64
Standard Base64 encoding with padding.
- Characters:
A-Z,a-z,0-9,+,/,= - Use case: Email-safe encoding, general data encoding
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
# Output: VQ6EAOKbQdSnFkRmVUQAAA==
Base64 URL-safe (base64url)
URL-safe Base64 without padding.
- Characters:
A-Z,a-z,0-9,-,_ - Use case: URLs, filenames, HTTP headers
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64url
# Output: VQ6EAOKbQdSnFkRmVUQAAA
Binary (bits)
Binary string representation.
- Characters:
0,1 - Use case: Bit-level analysis, debugging
idt convert 550e8400-e29b-41d4-a716-446655440000 -f bits
# Output: 0101010100001110100001000000000011100010...
Integer (int)
Decimal integer representation.
- Characters:
0-9 - Use case: Numeric comparison, database integer columns
idt convert 550e8400-e29b-41d4-a716-446655440000 -f int
# Output: 113059749145936325402354257176981405696
Note: 128-bit IDs produce very large integers that may overflow in some languages.
Bytes
Space-separated hexadecimal bytes.
- Use case: Byte-level inspection, debugging
idt convert 550e8400-e29b-41d4-a716-446655440000 -f bytes
# Output: 55 0e 84 00 e2 9b 41 d4 a7 16 44 66 55 44 00 00
Comparison Table
| Format | Length (128-bit) | URL-Safe | Human-Readable |
|---|---|---|---|
| canonical | 36 | No | Good |
| hex | 32 | Yes | Fair |
| base32 | 26 | Yes | Fair |
| base58 | ~22 | Yes | Good |
| base64 | 24 | No | Fair |
| base64url | 22 | Yes | Fair |
| bits | 128 | Yes | Poor |
| int | ~39 | Yes | Poor |
| bytes | 47 | No | Good |
Usage Examples
Convert Command
# Convert to specific format
idt convert "$ID" -f hex
idt convert "$ID" -f base64
idt convert "$ID" -f base58
# With case transformation
idt convert "$ID" -f hex -U # Uppercase
idt convert "$ID" -f hex -L # Lowercase
Generate with Format
# Generate in specific format
idt gen uuid -f hex
idt gen uuidv7 -f base64
Inspect Output
The inspect command shows multiple formats automatically:
$ idt inspect 550e8400-e29b-41d4-a716-446655440000
UUIDV4
550e8400-e29b-41d4-a716-446655440000
Hex 550e8400e29b41d4a716446655440000
Base64 VQ6EAOKbQdSnFkRmVUQAAA==
Int 113059749145936325402354257176981405696
Choosing a Format
| Use Case | Recommended Format |
|---|---|
| Database storage | hex or canonical |
| URLs and APIs | base64url or base58 |
| Display to users | canonical or base58 |
| Compact storage | base58 or base64url |
| Cross-system compatibility | hex |
| Debugging | bytes or bits |
ID Types Comparison
A comprehensive comparison of all ID types supported by idt.
Quick Reference
| Type | Bits | Sortable | Timestamp | Random Bits | String Length |
|---|---|---|---|---|---|
| UUIDv1 | 128 | No | Yes | ~14 | 36 |
| UUIDv3 | 128 | No | No | 0 | 36 |
| UUIDv4 | 128 | No | No | 122 | 36 |
| UUIDv5 | 128 | No | No | 0 | 36 |
| UUIDv6 | 128 | Yes | Yes | ~62 | 36 |
| UUIDv7 | 128 | Yes | Yes | 62 | 36 |
| ULID | 128 | Yes | Yes | 80 | 26 |
| NanoID | ~126 | No | No | ~126 | 21 |
| Snowflake | 64 | Yes | Yes | 0 | ~19 |
| KSUID | 160 | Yes | Yes | 128 | 27 |
| ObjectId | 96 | Partial | Yes | ~40 | 24 |
| XID | 96 | Yes | Yes | ~40 | 20 |
| TSID | 64 | Yes | Yes | ~22 | 13-17 |
Assigned IDs (validate & inspect only)
| Type | Chars | Sortable | Timestamp | Check Algorithm |
|---|---|---|---|---|
| EAN-13 | 13 | No | No | Mod 10 (1,3) |
| ISBN-13 | 13 | No | No | Mod 10 (1,3) |
| ISBN-10 | 10 | No | No | Mod 11 |
| ISIN | 12 | No | No | Luhn |
| EAN-8 | 8 | No | No | Mod 10 (1,3) |
| UPC-A | 12 | No | No | Mod 10 (1,3) |
| ISSN | 8 | No | No | Mod 11 |
| ISMN | 13 | No | No | Mod 10 (1,3) |
| ISNI | 16 | No | No | ISO 7064 MOD 11-2 |
| GTIN-14 | 14 | No | No | Mod 10 (1,3) |
| ASIN | 10 | No | No | None (format only) |
Detailed Comparison
Timestamp Precision
| Type | Precision | Epoch |
|---|---|---|
| UUIDv1 | 100 nanoseconds | October 15, 1582 |
| UUIDv6 | 100 nanoseconds | October 15, 1582 |
| UUIDv7 | Milliseconds | Unix epoch (1970) |
| ULID | Milliseconds | Unix epoch (1970) |
| Snowflake | Milliseconds | Custom (e.g., 2010, 2015) |
| KSUID | Seconds | May 13, 2014 |
| ObjectId | Seconds | Unix epoch (1970) |
| XID | Seconds | Unix epoch (1970) |
| TSID | Milliseconds | Unix epoch (1970) |
Collision Resistance
| Type | Same Millisecond | Different Nodes | Notes |
|---|---|---|---|
| UUIDv4 | Excellent | Excellent | 122 random bits |
| UUIDv7 | Good | Excellent | 62 random bits + timestamp |
| ULID | Excellent | Excellent | Monotonic + 80 random bits |
| NanoID | Excellent | Excellent | ~126 random bits |
| Snowflake | Limited | Requires coordination | 4096/ms per worker |
Encoding
| Type | Encoding | Case Sensitive | Alphabet |
|---|---|---|---|
| UUID | Hexadecimal | No | 0-9, a-f |
| ULID | Crockford Base32 | No | 0-9, A-Z (excluding I, L, O, U) |
| NanoID | Custom (default URL-safe) | Yes | A-Z, a-z, 0-9, -, _ |
| Snowflake | Decimal | N/A | 0-9 |
| KSUID | Base62 | Yes | 0-9, A-Z, a-z |
| ObjectId | Hexadecimal | No | 0-9, a-f |
| XID | Base32 | No | 0-9, a-v |
Use Case Recommendations
Database Primary Keys
| Requirement | Recommended Type |
|---|---|
| UUID compatibility required | UUIDv7 |
| Compact storage | ULID or Snowflake |
| Time-sortable queries | UUIDv7, ULID, or Snowflake |
| Maximum randomness | UUIDv4 |
| 64-bit integer column | Snowflake or TSID |
Distributed Systems
| Requirement | Recommended Type |
|---|---|
| No coordination needed | UUIDv7, ULID, UUIDv4 |
| Very high throughput | Snowflake |
| Cross-datacenter | UUIDv7 or ULID |
| Compact wire format | Snowflake (64-bit) |
User-Facing IDs
| Requirement | Recommended Type |
|---|---|
| Short URL slugs | NanoID (custom length) |
| Readable codes | NanoID (custom alphabet) |
| Compact but sortable | ULID |
| Standard format | UUID (canonical) |
Security-Sensitive
| Requirement | Recommended Type |
|---|---|
| Non-sequential | UUIDv4 or NanoID |
| Hide creation time | UUIDv4 or NanoID |
| Cryptographic randomness | UUIDv4 or NanoID |
Format Conversion Compatibility
Since ULID and UUID are both 128-bit, they can be converted between each other:
# ULID to UUID hex
idt convert 01ARZ3NDEKTSV4RRFFQ69G5FAV -f hex
# Can be stored in UUID column
# UUID to various formats
idt convert 550e8400-e29b-41d4-a716-446655440000 -f base64
Storage Size Comparison
| Type | Binary (bytes) | String (chars) | Typical DB Type |
|---|---|---|---|
| UUID | 16 | 36 | UUID, CHAR(36), BINARY(16) |
| ULID | 16 | 26 | CHAR(26), BINARY(16) |
| NanoID | ~16 | 21 | VARCHAR(21+) |
| Snowflake | 8 | ~19 | BIGINT |
| ObjectId | 12 | 24 | ObjectId, CHAR(24) |
Feature Matrix
| Feature | UUIDv4 | UUIDv7 | ULID | NanoID | Snowflake |
|---|---|---|---|---|---|
| Time-sortable | - | Yes | Yes | - | Yes |
| Extract timestamp | - | Yes | Yes | - | Yes |
| URL-safe | - | - | Yes | Yes | Yes |
| Fits in 64-bit | - | - | - | - | Yes |
| No coordination | Yes | Yes | Yes | Yes | - |
| Customizable | - | - | - | Yes | Yes |
| RFC standard | Yes | Yes | - | - | - |
| Widely supported | Yes | Growing | Growing | Growing | Yes |
Specification Links
| Type | Specification |
|---|---|
| UUID (v1-v5) | RFC 4122 |
| UUID (v6-v8) | RFC 9562 |
| ULID | github.com/ulid/spec |
| NanoID | github.com/ai/nanoid |
| Snowflake | Wikipedia |
| KSUID | github.com/segmentio/ksuid |
| ObjectId | MongoDB Docs |
| XID | github.com/rs/xid |
| TypeID | github.com/jetify-com/typeid |
| EAN-13 | GS1 EAN/UPC |
| ISBN | isbn-international.org |
| ISIN | ISO 6166 |
| ISSN | ISSN International Centre |
| ISMN | ISMN International Agency |
| ISNI | ISNI International Authority |
| GTIN-14 | GS1 GTIN |