Gerador de UUID: v4, v7, v5 e listas em lote
Um bom gerador de UUID entrega a versão que o seu banco de dados quer, na grafia exata que ele espera, e diz o que é de verdade qualquer UUID que você colar. Tudo abaixo roda no seu navegador.
Gerador de UUID
Nada por aqui ainda. Os UUIDs gerados ficam só neste navegador.
Qual versão um gerador de UUID deve te entregar?
Todo UUID tem 128 bits, escritos como 32 dígitos hexadecimais em cinco grupos, 8-4-4-4-12. Dois desses dígitos são de controle: o 13º é a versão, e o 17º carrega a variante (8, 9, a ou b nos UUIDs da RFC 9562). Todo o resto é o que a versão coloca ali: bits aleatórios, um timestamp, um contador ou um hash. Escolher a versão é, na prática, escolher o que você quer dentro da sua chave.
| Versão | O que tem dentro | Use para |
|---|---|---|
| v4 | 122 bits aleatórios | O padrão seguro: IDs que não revelam nada, chaves em tabelas pequenas e médias, IDs de correlação |
| v7 | Tempo Unix de 48 bits em ms, seguido de contador e bits aleatórios | Chaves primárias em tabelas com muito movimento, IDs de eventos e logs que você quer ordenados por data de criação |
| v1 | Tempo gregoriano em intervalos de 100 ns, sequência de relógio, nó | Só quando um sistema legado exige v1 |
| v6 | Os campos do v1, com o tempo guardado primeiro | Sistemas que já falam v1 mas precisam de chaves ordenáveis |
| v5 | SHA-1 de namespace + nome | O mesmo ID sempre para a mesma entrada: uma URL, um domínio, um SKU |
| v3 | MD5 de namespace + nome | Compatibilidade com um sistema antigo que já usava v3 |
| Nil / Max | Só zeros / só uns | Marcadores explícitos de "sem valor" e limites de intervalo, nunca como chave |
Minha regra prática: v4, a não ser que o ID seja uma chave de banco com muitos inserts; aí, v7. A própria RFC 9562 diz que as implementações devem usar v7 no lugar de v1 e v6 sempre que possível. O v5, baseado em nome, é o caso à parte: ele não serve para garantir unicidade ao longo do tempo, e sim para dar a mesma resposta duas vezes, que é exatamente o que você quer quando dois serviços precisam concordar sobre o ID de "https://example.com/item/42" sem conversar entre si. O guia v4 vs v7 mostra o lado dos índices nessa decisão.
Um alerta prático sobre o v7: os 12 primeiros dígitos hexadecimais são o momento de criação em milissegundos, legível por qualquer um. Cole 017f22e2-79b0-7cc3-98c4-dc0c0c07398f na aba Validar & decodificar e você vê o instante exato em que ele foi gerado. Se o ID aparece para usuários e o horário é sensível, entregue um v4.
Formatos: os mesmos 128 bits, sete grafias
A maioria dos erros de "UUID inválido" que já investiguei não vinha de IDs ruins, e sim da grafia errada para o sistema do outro lado. O gerador mantém os bits e muda só o texto, então o mesmo valor pode ir para qualquer um destes:
| Formato | Exemplo | Onde é esperado |
|---|---|---|
| Padrão em minúsculas | 6ba7b810-9dad-11d1-80b4-00c04fd430c8 | Tipo uuid do PostgreSQL, APIs JSON, a maioria das bibliotecas; é a forma canônica de saída |
| MAIÚSCULAS | 6BA7B810-9DAD-11D1-80B4-00C04FD430C8 | Ferramentas do Windows, saída do SQL Server |
| {Chaves} | {6ba7b810-9dad-11d1-80b4-00c04fd430c8} | Guid.ToString("B") do .NET, registro do Windows e COM |
| 32 hex, sem hífens | 6ba7b8109dad11d180b400c04fd430c8 | Nomes de arquivo, campos compactos de log |
| URN | urn:uuid:6ba7b810-9dad-11d1-80b4-00c04fd430c8 | XML e padrões que pedem uma URI |
| 0x hex | 0x6BA7B8109DAD11D180B400C04FD430C8 | Literal para uma coluna BINARY(16) do MySQL |
| Base64 | a6e4EJ2tEdGAtADAT9QwyA== | Armazenamento compacto ou tokens em campos só de texto |
A opção de separador (hífen, nenhum, ponto ou sublinhado) vale só para as formas padrão, maiúsculas e com chaves; uma URN com pontos deixaria de ser uma URN válida, então a ferramenta trava o separador nesse caso. Na entrada é o contrário: a RFC 9562 pede saída em minúsculas, mas leitura sem diferenciar maiúsculas de minúsculas, e o decodificador aceita todas as formas acima, menos Base64. Se você precisa da ordem de bytes do .NET ou entender as manias do SQL Server, leia UUID vs GUID.
Listas em lote para fixtures e arquivos de seed
A aba Em lote gera de 1 a 10.000 IDs de uma vez e exporta como texto puro, CSV com cabeçalho uuid, array JSON ou um comando INSERT INTO items (id) VALUES … pronto (troque a tabela e a coluna pelas suas). Dois detalhes importam mais do que a quantidade:
- Listas v7 saem em ordem estritamente crescente. Dez mil IDs são criados em poucos milissegundos, então a maioria compartilha o mesmo timestamp. Sem um contador, eles sairiam embaralhados dentro de cada milissegundo; com ele, a lista ordena igual como texto e como bytes, e a linha de informação confirma "em ordem estritamente crescente".
- v5 e v3 recebem nomes, um por linha. Cole uma coluna de domínios, URLs ou códigos de produto e você recebe um ID determinístico por linha, idêntico ao que o
uuid5()do Python retorna para o mesmo namespace e nome.
Dois UUIDs podem ser iguais?
Para IDs v4 aleatórios, a resposta honesta é "sim, com uma probabilidade que dá para calcular e depois parar de se preocupar". Com 122 bits aleatórios, a aproximação do paradoxo do aniversário dá:
Exemplo resolvido: você cria um bilhão de IDs v4, n = 109. Então n² = 1018, 2 × 2122 ≈ 1,063 × 1037, o expoente fica em torno de 9,4 × 10−20, e p ≈ 9,4 × 10−20. Com um trilhão de IDs, fica em torno de 9,4 × 10−14. Você precisa de algo como 2,7 × 1018 IDs para que a chance de uma única duplicata chegue a meio.
O risco real nunca é a matemática, e sim uma fonte aleatória fraca: um snippet copiado que usa Math.random(), um processo filho (fork) que reaproveita a seed, ou uma imagem de VM clonada com o mesmo estado. Este gerador de UUID tira cada bit aleatório de crypto.getRandomValues(), o gerador criptográfico do navegador. No v7, dois geradores independentes só colidem se escolherem o mesmo milissegundo e ainda baterem em cerca de 73 bits aleatórios (o contador começa com 41 bits aleatórios e outros 32 bits continuam aleatórios). Mesmo assim, coloque uma restrição de unicidade na coluna: não custa nada e transforma um problema teórico em um erro barulhento.
Validar e decodificar: o que um ID conta sobre si
Cole um UUID na aba Validar & decodificar e você recebe a forma canônica, a versão, a variante, o horário embutido no v1, v6 e v7 (em UTC e no seu horário local), a sequência de relógio e o nó do v1/v6, além das grafias hex para BINARY(16) e Base64. A verificação do nó diz se um ID v1 carrega um nó aleatório (bit multicast ligado, como a RFC 9562 recomenda) ou algo que parece o endereço de uma placa de rede real, o que é um vazamento de privacidade que vale a pena conhecer.
Cole uma coluna inteira e ela vira uma verificação de lista: quantas linhas são válidas, quais não são e por quê ("Foram encontrados 31 dígitos hexadecimais", "Os hífens precisam dividir os dígitos em 8-4-4-4-12"), quantas são duplicadas, se a lista está em ordem crescente e quais versões ela contém. É o jeito mais rápido que conheço de auditar um arquivo de importação antes que ele bata num índice único.
Ela também é rigorosa onde validadores antigos eram relaxados. Um UUID com dígito de versão 0 não é o UUID Nil, a menos que os 32 dígitos sejam zero; um ID com a variante legada da Microsoft (17º dígito c ou d) é bem formado, mas o dígito de versão não significa nada, e o resultado diz isso em vez de inventar uma versão.
Como guardar UUIDs sem se arrepender
- Use o tipo nativo. O
uuiddo PostgreSQL e ouniqueidentifierdo SQL Server ocupam 16 bytes. Uma coluna de texto de 36 caracteres ocupa mais que o dobro disso na tabela e em cada índice que a inclui. No MySQL, useBINARY(16); o formato 0x te dá o literal. - Escolha v7 para chaves clusterizadas ou com muitos inserts. Valores v7 novos entram no fim do índice, em vez de cair em páginas aleatórias.
- Mantenha uma única grafia canônica na sua API. Minúsculas com hífens. Compare sem diferenciar maiúsculas de minúsculas se você aceita entrada de outros sistemas.
- Nunca trate um UUID como segredo. A RFC 9562 diz para não presumir que UUIDs são difíceis de adivinhar. Links de redefinição de senha e chaves de API precisam de um token aleatório próprio.
- Não publique v1 com um endereço MAC real. Ele identifica a máquina e o momento. Esta ferramenta sempre usa um nó aleatório.
Para os comandos de uma linha que criam UUIDs em PostgreSQL, JavaScript, Python, Java e C#, veja como gerar um UUID no código.
De onde vêm os bits e como eu testo este gerador de UUID
Tudo acontece no seu navegador; a página não envia nada para lugar nenhum. Os bits aleatórios vêm de crypto.getRandomValues(). A versão 7 segue o método 1 da seção 6.2 da RFC 9562, com um contador de 42 bits (o mesmo esquema do uuid7() do Python): uma seed aleatória nova a cada milissegundo, mais um incremento para cada ID seguinte no mesmo milissegundo, e se o relógio andar para trás o último timestamp é reaproveitado, para a ordem nunca quebrar. As versões 1 e 6 contam ticks de 100 nanossegundos desde o início do calendário gregoriano, somam um tick por ID dentro do mesmo milissegundo e usam um nó aleatório com o bit multicast ligado. As versões 5 e 3 fazem o hash dos 16 bytes do namespace seguidos do nome em UTF-8 com SHA-1 ou MD5 e depois ajustam os bits de versão e variante, exatamente como fazem o texto da RFC 9562 e o módulo uuid do Python.
O script anterior deste site tinha um bug real que vale confessar: a conta do timestamp do v1 estourava um inteiro de 32 bits com sinal, então durante cerca de metade de cada sete minutos ele gerava IDs começando com um sinal de menos. A saída v7 também vinha fora de ordem dentro de um milissegundo. Os dois foram corrigidos, e estes estão entre os casos de controle contra os quais a ferramenta é testada a cada mudança:
| Entrada | Resultado esperado |
|---|---|
v5, namespace DNS, nome python.org | 886313e1-3b8a-5372-9b90-0c9aee199e5d |
v3, namespace DNS, nome python.org | 6fa459ea-ee8a-3ca4-894e-db77e160355e |
v5, namespace URL, https://uuid-generator.net/ | dc63ab62-ce65-5436-9a00-37417044f8cf |
| v1 no tempo Unix 1791450549290 ms | começa com ebbc68a0-c2f7-11f1 (o script antigo imprimia -14439760-…) |
Decodificar 017f22e2-79b0-7cc3-98c4-dc0c0c07398f | v7, 2022-02-22 19:22:22.000 UTC |
Decodificar c232ab00-9414-11ec-b3c8-9f6bdeced846 | v1, mesmo instante, sequência de relógio 13256, nó aleatório |
| 10.000 IDs v7 dentro de um milissegundo | todos únicos, em ordem estritamente crescente |
| UUID do namespace DNS em Base64 | a6e4EJ2tEdGAtADAT9QwyA== |
O decodificador lê o horário que o UUID diz carregar. Nada impede alguém de gravar qualquer timestamp num v7, então trate o horário decodificado como informação, não como prova.
Guias
Perguntas frequentes
Um UUID gerado aqui é realmente único?
Cada ID v4 carrega 122 bits aleatórios do gerador criptográfico do seu navegador; mesmo com um bilhão deles, a probabilidade de colisão fica em torno de 9,4 × 10^-20. Nada é guardado nem enviado, então ninguém mais vê os seus IDs.
Devo usar UUID v7 como chave primária?
Para tabelas com muitos inserts, sim: o v7 começa com um timestamp em milissegundos, então as chaves novas ficam próximas umas das outras no índice. Fique com o v4 quando o momento de criação não puder ficar visível para quem vê o ID.
GUID é a mesma coisa que UUID?
Sim, GUID é o nome que a Microsoft dá ao mesmo identificador de 128 bits. As diferenças são de costume: maiúsculas, chaves e ordem de bytes little-endian nos três primeiros grupos no .NET e no SQL Server.
Como tiro o timestamp de um UUID?
Cole o UUID na aba Validar & decodificar. As versões 1, 6 e 7 carregam um timestamp, e a ferramenta mostra o horário em UTC e no seu fuso local; v4 e v5 não contêm tempo nenhum.
Por que o mesmo nome sempre gera o mesmo UUID v5?
Um UUID v5 é um hash SHA-1 do namespace com o nome, então ele é determinístico por definição. Mude um caractere, o namespace ou uma barra no fim de uma URL e você recebe outro ID.
UUIDs diferenciam maiúsculas de minúsculas?
Não. A RFC 9562 pede que os geradores produzam minúsculas e que os parsers aceitem os dois casos. Guarde uma única grafia e compare sem diferenciar maiúsculas de minúsculas quando os IDs vierem de outros sistemas.
Atualizado em