Skip to content

Générer un UUID snippet

UUIDv4 (122 bits aléatoires) est l'identifiant par défaut partout.

UUIDv4 (122 bits aléatoires) est l'identifiant par défaut partout. L'unique règle dure : l'aléatoire doit être cryptographique — les générateurs basés sur Math.random ou mt_rand sont une surface d'attaque, car des identifiants devinables sont des identifiants forgés. La réponse des années 2020 pour les clés de base de données est v7 : un horodatage de 48 bits en millisecondes préfixe la queue aléatoire, donc les clés se trient par date de création et les insertions restent majoritairement en append au lieu de balader le B-tree au hasard. C et C++ sont omis : pas de générateur dans la stdlib.

Recette exécutable · 13 langagesOpen the uuid tool →
Crypto & Encodinguuidrandomidentifierv4v7

Every language

13 langages, copy-ready. One at a time with syntax highlighting, or all inline.

SQLSQLrunnable
SELECT gen_random_uuid(); -- v4 — Postgres 13+ built-in, no extension
-- v7 needs Postgres 18: SELECT uuidv7();

-- The index-locality payoff, concretely:
-- CREATE TABLE events (id uuid DEFAULT gen_random_uuid() PRIMARY KEY,
--                     ...);

Run the v4 line in the playground. A random v4 primary key scatters inserts across the whole B-tree at scale — v7 (or a ULID) keeps them append-mostly.

Run in the SQL playground →
JSJavaScript
const id = crypto.randomUUID(); // v4, cryptographic

console.log(id); // 36 chars with dashes

Node 14.17+ and secure browser contexts. v7 is not native — the uuid npm package ships uuidv7().

TSTypeScript
// UUIDv7 from scratch: 48-bit ms timestamp + random, version/variant stamped
function uuidv7(): string {
  const buf = crypto.getRandomValues(new Uint8Array(16));
  const ts = BigInt(Date.now());
  for (let i = 0; i < 6; i++) {
    buf[i] = Number((ts >> BigInt((5 - i) * 8)) & 0xffn); // big-endian
  }
  buf[6] = (buf[6] & 0x0f) | 0x70; // version 7
  buf[8] = (buf[8] & 0x3f) | 0x80; // RFC 4122 variant

  const hex = [...buf].map((b) => b.toString(16).padStart(2, '0')).join('');
  return `${hex.slice(0, 8)}-${hex.slice(8, 12)}-${hex.slice(12, 16)}-${hex.slice(16, 20)}-${hex.slice(20)}`;
}

The timestamp prefix is the whole point: v7 keys sort by creation time, so primary-key inserts cluster instead of scattering across the index.

GoGo
// stdlib has no UUID — v4 from crypto/rand
b := make([]byte, 16)
_, _ = rand.Read(b) // crypto/rand, NOT math/rand

b[6] = (b[6] & 0x0f) | 0x40 // version 4
b[8] = (b[8] & 0x3f) | 0x80 // RFC 4122 variant

id := fmt.Sprintf("%x-%x-%x-%x-%x",
	b[0:4], b[4:6], b[6:8], b[8:10], b[10:16])

google/uuid (uuid.New() and uuid.NewV7()) or gofrs/uuid in production — but crypto/rand is the non-negotiable line.

RsRust
use uuid::Uuid; // features = ["v4", "v7"]

fn main() {
    let v4 = Uuid::new_v4();
    let v7 = Uuid::now_v7(); // time-ordered
    println!("{v4} {v7}");
}

The uuid crate gates versions behind Cargo features — v7 needs the "v7" feature flag explicitly.

PHPPHP
// v4 from 16 cryptographic random bytes — dashes and bits are on you
$b = random_bytes(16);
$b[6] = chr((ord($b[6]) & 0x0f) | 0x40);
$b[8] = chr((ord($b[8]) & 0x3f) | 0x80);

$id = vsprintf(
    '%s%s-%s-%s-%s-%s%s%s',
    str_split(bin2hex($b), 4),
);

ramsey/uuid is the package (Uuid::uuid7() included). random_bytes is cryptographic — the old mt_rand snippets are attack surface.

PyPython
import uuid

print(uuid.uuid4())  # v4
print(uuid.uuid7())  # v7 — Python 3.14+

uuid7 landed in the 3.14 stdlib; on older Pythons the uuid6 package backports uuid6/uuid7/uuid8.

C#C#
Guid v4 = Guid.NewGuid();          // v4
Guid v7 = Guid.CreateVersion7();    // v7 — .NET 9+

string dashed = v4.ToString("D");  // dashes
string plain = v4.ToString("N");    // 32 hex chars, no dashes

Guid.NewGuid is v4; CreateVersion7 arrived in .NET 9. Trap: ToByteArray() returns the first 4 bytes reversed — never hand-parse it.

JvJava
import java.util.UUID;

UUID id = UUID.randomUUID(); // v4
System.out.println(id);

JDK ships v4 only. v7 needs java-uuid-generator (or the same 6-line bit-stamp from the Go example on a 6-byte timestamp).

SwSwift
import Foundation

let id = UUID().uuidString // v4 — note: UPPERCASE

uuidString is uppercase, unlike most languages' lowercase — lowercase it when the consumer case-matches. v7 needs a package (swift-uuid) today.

KtKotlin
import java.util.UUID

val id: UUID = UUID.randomUUID() // v4, dashed lowercase by default

Same java.util.UUID; toString() is lowercase-dashed, which is the format most APIs expect.

RbRuby
require 'securerandom'

id = SecureRandom.uuid # v4

SecureRandom wraps the OS CSPRNG — that is the entire reason it is called Secure. v7: the securerandom gem or hand-roll from Time.now.to_f.

ZigZig
const std = @import("std");

pub fn main() !void {
    var b: [16]u8 = undefined;
    std.crypto.random.bytes(&b); // OS CSPRNG

    b[6] = (b[6] & 0x0f) | 0x40; // version 4
    b[8] = (b[8] & 0x3f) | 0x80; // variant

    var hex: [36]u8 = undefined;
    _ = std.fmt.bufPrint(&hex, "{x}-{x}-{x}-{x}-{x}", .{
        b[0..4], b[4..6], b[6..8], b[8..10], b[10..16],
    }) catch unreachable;

    std.debug.print("{s}\n", .{hex});
}

{x} on a byte slice hex-encodes every element — the dashes land exactly at the RFC positions. std.crypto.random is always a CSPRNG.

Keep going

Try the interactive uuid tool →