8. Modelado de datos
MongoDB es schemaless, pero eso no significa que no debas pensar en tu modelo de datos.
Diferencias con SQL
En SQL, defines columnas a nivel de tabla. En MongoDB, defines campos a nivel de documento. Esto significa que cada documento puede tener campos diferentes.
// Esto es válido en MongoDB
db.users.insertMany([
{ name: 'Ana', age: 28 },
{ name: 'Carlos', age: 35, city: 'Madrid' },
{ name: 'Laura', email: 'laura@example.com' }
])
Referencias vs Documentos embebidos
Tienes dos formas principales de relacionar datos:
Referencias (similar a foreign keys)
// Colección employees
{
_id: 698,
name: 'Duncan',
manager: 485 // Referencia al manager
}
// Para obtener el manager:
var employee = db.employees.findOne({ _id: 698 })
var manager = db.employees.findOne({ _id: employee.manager })
Documentos embebidos
{
_id: 501,
name: 'Ghanima',
family: {
mother: 'Chani',
father: 'Paul',
brother: 485
}
}
// Buscar por campos embebidos usa notación de punto
db.employees.find({ 'family.mother': 'Chani' })
¿Cuándo usar cada uno?
Usa referencias cuando:
- Los datos se usan en diferentes contextos
- Los datos cambian frecuentemente
- Necesitas evitar duplicación
- Los documentos son muy grandes
Usa documentos embebidos cuando:
- Los datos casi siempre se consultan juntos
- Los datos no cambian mucho
- Quieres mejor rendimiento (una sola consulta)
- Los documentos son pequeños
Arrays de valores
MongoDB maneja arrays como ciudadanos de primera clase:
{
name: 'Ana',
hobbies: ['lectura', 'programación', 'música']
}
// Buscar usuarios que tienen un hobby específico
db.users.find({ hobbies: 'programación' })
Los arrays también pueden contener documentos:
{
name: 'Ana',
addresses: [
{ type: 'casa', city: 'Madrid', street: 'Gran Vía 1' },
{ type: 'trabajo', city: 'Madrid', street: 'Alcalá 42' }
]
}
// Buscar por campos dentro del array
db.users.find({ 'addresses.city': 'Madrid' })
Desnormalización
A diferencia de SQL donde evitas duplicar datos, en MongoDB a veces duplicar datos es la mejor opción:
// En lugar de solo el user_id
{
post: 'Mi primer post',
user_id: 123
}
// Puedes almacenar también el nombre
{
post: 'Mi primer post',
user: {
id: 123,
name: 'Ana'
}
}
Ventajas:
- Una sola consulta para obtener todo
- Mejor rendimiento
- Los datos se leen juntos
Desventajas:
- Si Ana cambia su nombre, debes actualizar múltiples documentos
- Más espacio de almacenamiento
Límite de tamaño
Cada documento tiene un límite de 16 MB. Si necesitas almacenar archivos grandes, usa GridFS.
Ejemplo práctico: blog
Para un blog, podrías modelar:
Opción 1: Comentarios en colección separada
// Posts
{ _id: 1, title: 'Mi post', content: '...' }
// Comments
{ post_id: 1, author: 'Ana', text: 'Gran post' }
Opción 2: Comentarios embebidos
{
_id: 1,
title: 'Mi post',
content: '...',
comments: [
{ author: 'Ana', text: 'Gran post' },
{ author: 'Carlos', text: 'Interesante' }
]
}
Opción 3: Híbrida (recomendada)
{
_id: 1,
title: 'Mi post',
content: '...',
// Primeros comentarios embebidos
recent_comments: [
{ author: 'Ana', text: 'Gran post' },
{ author: 'Carlos', text: 'Interesante' }
],
total_comments: 152
}
// El resto en colección separada
Esto te da rendimiento (primeros comentarios en una consulta) y escalabilidad (si hay muchos comentarios).
This work is under a Attribution-NonCommercial-NoDerivatives 4.0 International license.
Desafíos de programación atemporales y multiparadigmáticos
Te encuentras ante un librillo de actividades, divididas en 2 niveles de dificultad. Te enfrentarás a los casos más comunes que te puedes encontrar en pruebas técnicas o aprender conceptos elementales de programación.
Buy the book
Comments
There are no comments yet.