UUID v4 ou v7: qual usar e como gerar em código

O UUID v4 é totalmente aleatório, e o UUID v7 começa com a data e a hora em milissegundos, o que mantém os identificadores em ordem de criação. Este guia compara os dois, explica o efeito no desempenho de índices de banco de dados e mostra como gerar UUID v4 e v7 em JavaScript e Python.

Por Leonardo Gaertner · Publicado em

A diferença em uma frase

O v4 tem 122 bits aleatórios. O v7, definido na RFC 9562, usa os 48 primeiros bits para os milissegundos desde 1970 e o restante, exceto os bits de versão e variante, é aleatório.

Como reconhecer a versão

  • O primeiro caractere do terceiro grupo é a versão: 4 ou 7.
  • No v7, os 12 primeiros caracteres hexadecimais guardam a data de criação (veja como ler mais abaixo).

O validador de UUID informa a versão e a variante de qualquer UUID.

Quando usar o v4

  • Quando o identificador não deve revelar quando foi criado.
  • Em identificadores expostos em URLs e APIs públicas, onde a ordem de criação não pode ser deduzida.
  • Quando não há uma tabela grande com índice sobre o identificador.

Para gerar v4, use o gerador de UUID, ou crypto.randomUUID() no JavaScript e uuid.uuid4() no Python.

Quando usar o v7

Em bancos de dados, a chave primária costuma ter um índice em árvore. Com v4, cada novo registro cai em um ponto aleatório do índice, o que espalha as gravações e pode aumentar o trabalho de reorganização em tabelas grandes. Com v7, os novos valores são maiores que os anteriores, então vão para o fim do índice, como acontece com um contador.

Isso também permite ordenar pelo identificador para obter a ordem de criação, e ler a data de criação pelo próprio UUID. O preço é que o v7 revela o instante de criação.

  • Não use o v7 onde a data de criação for uma informação sensível.
  • Dois v7 criados no mesmo milissegundo não têm ordem garantida entre si com a implementação simples abaixo. A RFC descreve técnicas com contador para isso.

Gerar UUID em JavaScript

O v4 já vem pronto: crypto.randomUUID() funciona no navegador (em páginas seguras, com HTTPS) e no Node.js. O v7 pode ser montado assim:

JavaScript
function uuidv7() {
  const bytes = crypto.getRandomValues(new Uint8Array(16));
  const ms = BigInt(Date.now());

  // Os 48 primeiros bits são os milissegundos desde 1970
  bytes[0] = Number((ms >> 40n) & 0xffn);
  bytes[1] = Number((ms >> 32n) & 0xffn);
  bytes[2] = Number((ms >> 24n) & 0xffn);
  bytes[3] = Number((ms >> 16n) & 0xffn);
  bytes[4] = Number((ms >> 8n) & 0xffn);
  bytes[5] = Number(ms & 0xffn);

  bytes[6] = (bytes[6] & 0x0f) | 0x70; // versão 7
  bytes[8] = (bytes[8] & 0x3f) | 0x80; // variante da RFC

  const hex = Array.from(bytes, (b) => b.toString(16).padStart(2, '0')).join('');
  return hex.replace(/^(.{8})(.{4})(.{4})(.{4})/, '$1-$2-$3-$4-'); // 8-4-4-4-12
}

Usa o gerador aleatório seguro do navegador e do Node.js.

Para ler a data de criação de um v7:

JavaScript
// Em um UUID v7, os 12 primeiros caracteres hexadecimais são os milissegundos desde 1970
function dataDoUuidV7(uuid) {
  const ms = parseInt(uuid.replace(/-/g, '').slice(0, 12), 16);
  return new Date(ms);
}

Gerar UUID em Python

O v4 vem na biblioteca padrão, com uuid.uuid4(). Para o v7:

Python
import os
import time
import uuid


def uuid7() -> uuid.UUID:
    ms = time.time_ns() // 1_000_000
    b = bytearray(os.urandom(16))
    b[0:6] = ms.to_bytes(6, "big")  # 48 bits de milissegundos desde 1970
    b[6] = (b[6] & 0x0F) | 0x70  # versão 7
    b[8] = (b[8] & 0x3F) | 0x80  # variante da RFC
    return uuid.UUID(bytes=bytes(b))

Cuidados ao usar UUID

  • UUID não é segredo: não use como senha, token de sessão ou chave de API. Para isso, gere valores aleatórios próprios com um gerador seguro e mais bits.
  • Se o banco tiver o tipo UUID, use-o em vez de texto: ele ocupa 16 bytes em vez de 36 caracteres.
  • Não misture versões sem necessidade: um índice com v4 e v7 perde a vantagem da ordem.

Achou um erro neste guia? Avise por e-mail.

Perguntas frequentes

O UUID v7 substitui o v4?

Não. O v4 continua sendo a melhor escolha quando o identificador não deve revelar a data de criação. O v7 é melhor quando o identificador vira chave de uma tabela grande e a ordem de criação ajuda.

O UUID v7 é seguro para usar como token?

Não. Ele guarda a data de criação nos primeiros bits e tem menos bits aleatórios que um token de segurança. UUID serve para identificar registros, não para ser segredo.

Dá para extrair a data de um UUID v7?

Sim. Os 12 primeiros caracteres hexadecimais são os milissegundos desde 1970, e a função deste guia converte isso em uma data.

UUID e GUID são a mesma coisa?

Na prática, sim. GUID é o nome usado pela Microsoft para o mesmo tipo de identificador de 128 bits.