¿Qué es una base de columnas anchas como Cassandra, y en qué se diferencia su modelo de datos de una tabla relacional?
Las tablas de Cassandra parecen tablas hasta que notas que la clave primaria en realidad cumple dos trabajos distintos —uno elige la máquina, el otro el orden— y esa división es todo el modelo.
APRENDE HACIENDOPon a prueba tu intuición3 pasos
¿Qué es una base de columnas anchas como Cassandra, y en qué se diferencia su modelo de datos de una tabla relacional?
Usa los ejemplos y la explicación de la lección para comprobar tu idea.
Reflexión personal. No se envía a ningún servicio de IA.#Dos claves que cumplen dos trabajos distintos
La sentencia CREATE TABLE de Cassandra se parece engañosamente a SQL —columnas, tipos, una cláusula PRIMARY KEY— y es precisamente eso lo que confunde a la gente. La clave primaria en Cassandra no es una sola cosa, son dos cosas disfrazadas con la misma sintaxis:
PRIMARY KEY ((customer_id), order_time)^^^^^^^^^^^^ ^^^^^^^^^^clave de partición columna de clustering
La clave de partición decide dónde: qué nodo (en realidad, qué conjunto de nodos réplica) del clúster es dueño de ese dato. Cassandra aplica un hash con un algoritmo de hashing consistente (murmur3 por defecto) a la clave de partición para obtener un token, y cada nodo del anillo es dueño de un rango de tokens. Toda fila con la misma clave de partición cae en las mismas réplicas, punto — no existe un join entre nodos para volver a encontrarlas.
La(s) columna(s) de clustering deciden el orden: dentro de esa única partición, las filas se guardan ordenadas por las columnas de clustering, en disco, listas para un escaneo de rango. Por eso "dame los 20 pedidos más recientes del cliente 4471" es de las consultas más baratas que Cassandra puede correr: es una lectura de una sola partición que ya está ordenada por order_time, sin necesidad de calcular ningún ORDER BY al momento de la consulta.
#Dónde vive físicamente la partición
Alejando la mirada de una tabla al clúster completo, la clave de partición es también lo que distribuye los datos entre máquinas. El hashing consistente hace que agregar o quitar un nodo solo reacomode una fracción de los datos (no todo, como pasaría con un sharding ingenuo tipo hash(clave) % N), y el factor de replicación (digamos, 3) determina cuántos nodos guardan una copia de cada partición.
#Por qué esto lo vuelve un diseño guiado por la consulta, no por la entidad
Un esquema relacional se diseña alrededor de entidades y se normaliza para evitar duplicación; cómo consultarlo se resuelve después, porque el planificador y los índices pueden adaptarse a casi cualquier WHERE/JOIN que escribas. Cassandra invierte ese orden de operaciones: la consulta va primero, y la tabla se diseña para que la consulta que necesita atender sea una lectura de una sola partición.
Eso tiene consecuencias reales:
- Una tabla por patrón de consulta es lo normal, no un mal olor. Si necesitas tanto "pedidos de un cliente, del más nuevo al más viejo" como "pedidos con cierto estado, de todos los clientes", típicamente son dos tablas distintas —
orders_by_customeryorders_by_status— cada una con su clave de partición/clustering pensada para su propia consulta, mantenidas sincronizadas escribiendo en ambas ante cada cambio de pedido. - Los índices secundarios existen, pero son una trampa para columnas de alta cardinalidad. Un índice secundario nativo sobre una columna como
emailtermina consultando a todos los nodos del clúster en cada consulta, porque Cassandra no sabe qué partición guarda un correo dado: tiene que preguntarle a todos. Eso es exactamente lo opuesto a la lectura de una sola partición sobre la que está construido todo el modelo. - Los joins ad hoc no existen en absoluto. No hay operador de join. Si necesitas el pedido junto con datos del cliente, desnormalizas el nombre y el correo del cliente directamente dentro de la fila del pedido al momento de escribir, y aceptas que una actualización del cliente implica actualizar (o aceptar que quede desactualizado) cada lugar donde lo copiaste.
- La consistencia es ajustable por consulta, no fija globalmente. Con factor de replicación 3, una lectura o escritura puede pedir nivel de consistencia
ONE(rápido, puede leer datos desactualizados de una réplica que no se ha puesto al día),QUORUM(una mayoría de réplicas coinciden, el punto medio habitual) oALL(todas las réplicas, lo más lento y lo menos disponible si una está caída). Es la versión práctica y graduable del lado AP de CAP: puedes comprar más consistencia pagando latencia y disponibilidad, por consulta, según haga falta.
#Comparación rápida
| Tabla relacional | Tabla de columnas anchas de Cassandra | |
|---|---|---|
| Ubicación de la fila | La decide el motor de almacenamiento, se encuentra vía un índice | La decide el hash de la clave de partición |
| Orden de las filas | El que pidas con ORDER BY al consultar | Fijo desde la escritura, por las columnas de clustering |
| Joins | De primera clase, optimizados por el planificador | Ninguno: se desnormaliza al escribir |
| Diseño de esquema | Modelar entidades, normalizar | Modelar consultas, una tabla por patrón de acceso |
| Consistencia | Fuerte por defecto (un solo primario) | Ajustable por solicitud (ONE/QUORUM/ALL) |
| Escalar horizontalmente | Suele necesitar una estrategia de sharding externa | Incorporado, vía hashing consistente |
🧠 Check your understanding
0/2 · 0/2 answered1. En Cassandra, una tabla se define con `PRIMARY KEY ((customer_id), order_time)`. ¿Qué determina en qué nodo del clúster se guarda una fila dada?
2. Un equipo agrega un índice secundario sobre una columna `status` con solo 4 valores posibles, esperando búsquedas rápidas como daría un índice relacional. ¿Por qué esto suele rendir mal a escala en Cassandra?