
PostgreSQL o MongoDB: JSON flexible no significa la misma actualización

PostgreSQL suele ser la elección más directa cuando predominan las relaciones entre entidades, las consultas que las combinan y las transacciones que deben modificarlas juntas. MongoDB encaja mejor cuando los datos se leen y cambian principalmente como documentos autónomos. Guardar atributos flexibles en JSONB o BSON no hace equivalentes las actualizaciones de un campo anidado.
La decisión se aclara con cinco cargas: una transacción relacional, un documento de estructura cambiante, una actualización parcial, una consulta entre entidades y la distribución horizontal. Importa identificar cuál domina, cuánto crecen los datos y qué consistencia exige la aplicación; ninguna cifra de rendimiento sustituye esas condiciones.
Transacción relacional: qué debe cambiar al mismo tiempo

Supongamos, como ejemplo, un pedido que registra un pago y descuenta existencias. Si el cliente, el pago y el inventario tienen vida propia y se consultan por separado, las tablas relacionadas y una transacción de PostgreSQL expresan con claridad qué cambios deben confirmarse juntos. También permiten declarar claves y restricciones que protegen las relaciones cuando otra operación intenta modificar los mismos datos.
La documentación de atomicidad de MongoDB distingue la escritura atómica de un documento de las transacciones entre documentos, que también admite y que habitualmente cuestan más que una escritura individual. Por eso el límite relevante es el del documento: si los cambios que deben ser indivisibles caben en él, el modelo documental resulta sencillo. Si las operaciones habituales cruzan varios documentos, habrá que contar las transacciones y diseñar cómo se mantienen las referencias, sin suponer que la flexibilidad del esquema resuelve la consistencia.
Documento cambiante: qué datos se leen juntos

En un catálogo hipotético, una ficha puede tener dimensiones y otra, materiales o variantes. MongoDB permite que los documentos de una colección tengan campos distintos y que una ficha reúna los datos que la aplicación recupera juntos. PostgreSQL también puede conservar atributos variables en JSONB junto a columnas estables, como el identificador o el estado del producto. La diferencia útil no es la presencia de JSON, sino dónde conviene poner el límite de cada entidad.
Si una ficha incorpora una lista que crece sin control, leerla completa y modificarla puede volverse más costoso aunque al principio fuera cómoda de modelar. Si ciertos atributos pertenecen a una entidad compartida por muchos productos, copiarlos dentro de cada ficha simplifica algunas lecturas pero multiplica los lugares que habrá que actualizar. Para representar esta carga hacen falta fichas pequeñas y grandes con una distribución verosímil, más una lectura completa y otra que solicite solo los campos usados. Así se distingue la ventaja de recuperar un documento entero del coste de transportar datos que la consulta no necesita.
Actualización parcial: la sintaxis no describe todo el trabajo
La documentación de JSONB de PostgreSQL 18 muestra cómo modificar un valor anidado y advierte que cualquier actualización bloquea la fila completa; recomienda mantener manejable el tamaño del documento para reducir la contención. La ruta de un campo en la sentencia SQL indica el cambio lógico, pero la fila sigue siendo la unidad de concurrencia. Por eso un atributo que cambia constantemente puede merecer una columna propia o una entidad separada, sobre todo si comparte una fila grande con datos que cambian poco.
Una evaluación técnica publicada por MongoDB contrapone las nuevas versiones de fila de PostgreSQL con las operaciones dirigidas mediante $set sobre BSON; su prueba sintética usó 256 usuarios concurrentes durante 30 minutos sobre unos 13 millones de documentos, con AWS RDS PostgreSQL m5.xlarge frente a MongoDB Atlas M40 con escalado automático a M50. En esa configuración, MongoDB mantuvo una tasa de actualizaciones más estable. Los despliegues y recursos eran diferentes, así que el resultado describe esa carga y esas configuraciones, no una ventaja fija del motor ante cualquier documento.
$set identifica el campo que se modifica, pero por sí solo no promete una escritura física idéntica en todos los casos ni una latencia determinada. El tamaño del documento, los índices y las escrituras concurrentes pueden cambiar el coste observado. Una comparación de actualización parcial debe repetir el cambio de un atributo anidado con tamaños representativos y con los índices que realmente necesitará la aplicación; medir solo la operación sin índices puede ocultar el trabajo de mantenerlos.
Consultas con relaciones: importa el modelo, no solo la latencia
Una consulta que cruza pedidos, clientes, pagos y productos plantea una carga distinta de recuperar una ficha por identificador. PostgreSQL permite expresar esas relaciones con JOIN y conservar cada entidad en un lugar; sus índices pueden responder a los filtros que se usan con frecuencia. MongoDB puede reunir colecciones mediante agregaciones o insertar datos relacionados en un documento. La segunda opción reduce ciertas lecturas entre colecciones, pero puede exigir actualizar copias cuando cambia un dato compartido.
Comparar ambas bases con el mismo esquema literal favorecería unas operaciones y perjudicaría otras por una decisión de modelado ajena a la necesidad del producto. Tiene más sentido ejecutar las mismas preguntas de negocio sobre un modelo razonable para cada motor: buscar por identificador, filtrar entidades relacionadas y devolver solo los campos requeridos. La selectividad del filtro, los índices y la cantidad de filas o documentos examinados explican mejor una latencia que la etiqueta «SQL» o «documental». Si las relaciones cambian tanto como se consultan, el mantenimiento de datos duplicados entra en la cuenta.
Escalado horizontal: la clave de partición cambia las consultas

MongoDB incorpora sharding para repartir colecciones entre shards. La guía oficial de sharding explica que una consulta con la clave de partición, o el prefijo pertinente de una clave compuesta, puede dirigirse a los shards necesarios; sin ella, la consulta puede enviarse a todos. Repartir almacenamiento y escrituras, por tanto, exige conocer las rutas de consulta. Una clave mal distribuida también puede concentrar actividad en una parte del clúster.
La carga representativa combina consultas dirigidas y consultas sin esa clave, junto con escrituras distribuidas según la demanda esperada. Hay que observar tanto el reparto de operaciones como el coste de reunir respuestas de varios shards. Para PostgreSQL, la comparación debe especificar la arquitectura que se propone para crecer: una instancia única y un clúster fragmentado resuelven problemas operativos distintos. El número de nodos por sí solo tampoco indica si las consultas frecuentes conservarán una ruta eficiente.
Qué comparan realmente los benchmarks
El repositorio MDM Golden Record Benchmark define una carga configurable de un millón de registros y una salida con latencias P50, P95 y P99; su perfil de producción enfrenta Amazon RDS PostgreSQL con Amazon DocumentDB, servicio compatible con MongoDB. El repositorio también ofrece un perfil local con MongoDB. Son configuraciones diferentes: un resultado del perfil de producción no debe presentarse como una medición de MongoDB Atlas o de MongoDB instalado por cuenta propia. Las tablas incluidas como ejemplos de salida explican el formato de los resultados, pero no bastan para atribuir una ventaja medida a cualquiera de los motores.
Una medición que pretenda orientar esta elección debe declarar versiones de servidor, tipo y tamaño del despliegue, distribución y crecimiento de documentos, índices, concurrencia, mezcla de lecturas y escrituras, y garantías de lectura y confirmación de escritura. También debe conservar los percentiles junto al rendimiento total: una media puede ocultar esperas en operaciones que afectan directamente al usuario. Sin esas condiciones, dos números de latencia pueden corresponder a cargas incompatibles.
El coste de cambiar de motor después incluye rediseñar límites de transacción, consultas, referencias e índices, además de trasladar registros. Pasar de relaciones a documentos puede introducir duplicación; recorrer el camino inverso puede exigir separar entidades y reconstruir vínculos. Conviene decidir por la carga y la consistencia que dominan, y comprobar que el modelo elegido seguirá siendo comprensible cuando crezcan los documentos o cambien las preguntas que hace la aplicación.
Lee también:
Artículos relacionados


DuckDB o SQLite: la consulta analítica decide antes que el archivo

Supabase o Firebase: trabajar sin conexión puede decidir la elección

Redis o Memcached: más funciones pueden perder frente a más hilos

REST o GraphQL: ahorrar solicitudes puede aumentar la complejidad

FastAPI o Django: más peticiones no sustituyen ORM y transacciones
Suscríbete a nuestro boletín
Reciba las últimas noticias sobre Web3, IA y criptomonedas directamente en su bandeja de entrada.