CodeGym /Cursos /SQL SELF /Generación de identificadores únicos

Generación de identificadores únicos

SQL SELF
Nivel 16 , Lección 0
Disponible

Cuando los ordenadores empezaron a conectarse activamente en red, surgió un problema simple pero muy serio: ¿cómo garantizar que dos dispositivos diferentes, en partes distintas del mundo, no generen el mismo identificador?

Imagínate: dos servidores, uno en Tokio y otro en Berlín, crean identificadores para objetos de forma independiente. Si por casualidad generan el mismo ID — los datos pueden mezclarse, sobrescribirse, y el sistema puede caerse.

Así, en los años 90, en la época del boom de los sistemas distribuidos y los protocolos de red, en las entrañas de Microsoft y Open Software Foundation (OSF) nació la idea del GUIDGlobally Unique Identifier, o sea, identificador globalmente único.

GUID (y en el estándar ISO — UUID, Universally Unique Identifier) — es un número de 128 bits, que se ve, por ejemplo, así:

550e8400-e29b-41d4-a716-446655440000

Es como una huella digital: es tan largo y caótico que la probabilidad de colisión (que dos identificadores coincidan) es prácticamente nula.

Se crea usando:

  • el tiempo,
  • números aleatorios,
  • la dirección MAC del dispositivo (en versiones antiguas),
  • e incluso funciones hash criptográficas.

¿Por qué era importante esto? Pues porque GUID permitió crear identificadores únicos sin servidor central, sin coordinación, sin bloqueos ni retrasos. Fue una auténtica salvación para:

  • bases de datos distribuidas,
  • protocolos de red,
  • flujos de documentos,
  • y, por supuesto, APIs modernas.

UUID en PostgreSQL

GUID/UUID se usa en todas partes — desde PostgreSQL hasta servicios en la nube. Son los constructores invisibles de Internet moderno: sin ellos, no podríamos conectar el mundo tan fácilmente.

De hecho, es simplemente un número aleatorio muy largo de 16 bytes, escrito en formato hexadecimal. Simplemente un número entero muy largo.

Este tipo de dato es perfecto si necesitas garantizar la unicidad de los valores a nivel de todo el sistema, sin depender de un generador centralizado de identificadores. Es especialmente útil en sistemas distribuidos o cuando los datos se generan en diferentes servidores.

¿Por qué no usar simplemente INTEGER?

Parece lógico preguntarse, ¿para qué usar UUID si puedes usar un número auto-incremental como identificador? Vamos a verlo:

Unicidad global: Si tu base de datos funciona en varios servidores, garantizar la unicidad de INTEGER es complicado. Con UUID este problema desaparece.

Seguridad y ocultación de datos: UUID es más difícil de adivinar que un número secuencial. Esto reduce el riesgo de fuga de información por identificadores predecibles (por ejemplo, /users/1, /users/2).

Sistemas distribuidos: Si los datos se generan en diferentes partes del sistema, un INTEGER auto-incremental no sirve sin una sincronización complicada.

Otra ventaja de UUID — es un estándar soportado en muchos lenguajes de programación y sistemas de almacenamiento de datos.

Ventajas de usar UUID

Las principales ventajas:

  • Unicidad: se garantiza la unicidad del identificador, incluso si los datos se crean en diferentes servidores o sistemas.
  • Flexibilidad: puedes usarlo para claves primarias, claves foráneas y otras tareas.
  • Escalabilidad: muy útil cuando trabajas con bases de datos distribuidas.

Pero UUID también tiene sus desventajas:

  • Tamaño: UUID ocupa más espacio en memoria (16 bytes) que INTEGER (4 bytes).
  • Legibilidad: es más difícil de leer y recordar.

Generar UUID en PostgreSQL

Función incorporada gen_random_uuid()

En PostgreSQL desde la versión 13 hay una función incorporada gen_random_uuid() para generar UUID aleatorios. Esta función devuelve un identificador único que puedes usar como valor para una columna de tipo UUID.

Ejemplo:

SELECT gen_random_uuid();

Resultado:

d17fc23b-22e5-4fcb-bf86-1b4c766d77b7

Asegúrate de que la extensión pgcrypto está instalada (para PSQL 1-12)

En versiones antiguas de PostgreSQL (hasta la versión 13) la función gen_random_uuid() está disponible después de instalar la extensión pgcrypto. Si en el curro te obligan a usarla, puedes salvar la situación ejecutando el comando:

CREATE EXTENSION IF NOT EXISTS "pgcrypto";

Esto te permitirá usar la generación de UUID aleatorios.

Usar UUID como clave foránea

UUID es muy cómodo para crear relaciones entre tablas. Supón que tienes una tabla de usuarios:

id name email
d17fc23b-22e5-4fcb-bf86-1b4c766d77b7 Alice alice@example.com
a1d3e15a-abc1-4b51-a320-2d4c859f7467 Bob bob@example.com
3c524998-5c24-4e73-836d-a4c6bb3cafcd Charlie charlie@example.com

Crear la tabla orders

Vamos a crear la tabla orders, donde user_id será una clave foránea que referencia a id en la tabla users.

order_id user_id order_date
1a5b7d9c-b1a2-4f8e-9e7a-0a1111111111 d17fc23b-22e5-4fcb-bf86-1b4c766d77b7 2024-10-15 10:00:00
2b6c8e0d-c2b3-5a9f-af8b-1b2222222222 a1d3e15a-abc1-4b51-a320-2d4c859f7467 2024-10-15 10:05:00
3c7d9f1e-d3c4-6baf-bc9c-2c3333333333 3c524998-5c24-4e73-836d-a4c6bb3cafcd 2024-10-15 10:10:00
4d8eaf2f-e4d5-7cb0-cdab-3d4444444444 d17fc23b-22e5-4fcb-bf86-1b4c766d77b7 2024-10-15 10:15:00
5e9fb030-f5e6-8dc1-debc-4e5555555555 a1d3e15a-abc1-4b51-a320-2d4c859f7467 2024-10-15 10:20:00

El campo user_id está relacionado con el campo id de la tabla users, lo que permite crear relaciones entre usuarios y sus pedidos.

Consulta de datos con JOIN

Veamos cómo se relacionan los datos en las tablas users y orders:

SELECT 
    u.id AS user_id, 
    u.name, 
    o.order_id, 
    o.order_date 
FROM users u
JOIN orders o ON u.id = o.user_id;

Resultado:

user_id name order_id order_date
d17fc23b-22e5-4fcb-bf86-1b4c766d77b7 Alice a1d3e15a-abc1-4b51-a320-2d4c859f7467 2024-10-20 12:34:56

Escenarios principales de uso de UUID

Identificadores de usuarios y pedidos: en sistemas distribuidos donde los datos pueden venir de diferentes fuentes.

Marcas para API: UUID se usa mucho en REST API para identificar entidades.

Sincronización global de datos: por ejemplo, cuando los datos se recogen de diferentes servidores.

Errores típicos y particularidades

Intentar generar UUID manualmente: mejor usa funciones incorporadas como gen_random_uuid() para evitar errores.

Uso excesivo: no uses UUID donde basta con un INTEGER auto-incremental. Por ejemplo, en tablas locales que nunca se van a escalar.

Tamaño: UUID ocupa más espacio, lo que puede afectar el rendimiento de las consultas, especialmente al indexar.

2
Tarea
SQL SELF, nivel 16, lección 0
Bloqueada
Generación de UUID
Generación de UUID
2
Tarea
SQL SELF, nivel 16, lección 0
Bloqueada
Vinculación de UUID en tablas relacionadas
Vinculación de UUID en tablas relacionadas
Comentarios
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION