Persistencia

La capacidad de almacenar datos de forma duradera para que sobrevivan al cierre de la aplicación o del servidor.

¿Qué es la persistencia de datos?

Cuando cerrás una app o se reinicia un servidor, ¿qué pasa con la información? Si los datos estaban solo en la memoria RAM, se pierden. La persistencia es lo que garantiza que los datos sobrevivan a esos eventos. Cada vez que un usuario crea una cuenta, sube una foto o escribe un mensaje, esos datos necesitan guardarse en algún lugar permanente, generalmente una base de datos o un sistema de archivos.

Tipos de almacenamiento

No todos los datos se persisten de la misma forma. Dependiendo de qué tan duradero y accesible necesitás que sea, hay diferentes opciones:

TipoDuraciónEjemploUso típico
Memoria (RAM)Mientras corre el procesoVariables en tu códigoDatos temporales, cálculos
Base de datosPermanentePostgreSQL, MongoDBDatos del negocio
Sistema de archivosPermanenteDisco del servidor, S3Imágenes, PDFs, videos
LocalStoragePermanente (en el navegador)localStorage.setItem()Preferencias del usuario
SessionStorageMientras dure la pestañasessionStorage.setItem()Datos de la sesión actual
// Data in memory: lost on restart let counter = 0; // Data persisted in database: survives await db.query( 'INSERT INTO visits (page, date) VALUES ($1, $2)', ['/home', new Date()] ); // Data in localStorage: persists in the browser localStorage.setItem('theme', 'dark');

Transacciones: todo o nada

Cuando una operación involucra guardar varios datos relacionados, necesitás transacciones. Una transacción agrupa varias operaciones y garantiza que se ejecuten todas o ninguna. Pensá en una transferencia bancaria: tenés que restar plata de una cuenta y sumar en otra. Si falla a la mitad, no querés que se reste pero no se sume.

const trx = await db.transaction(); try { await trx.query( 'UPDATE accounts SET balance = balance - $1 WHERE id = $2', [1000, originAccount] ); await trx.query( 'UPDATE accounts SET balance = balance + $1 WHERE id = $2', [1000, destinationAccount] ); await trx.commit(); // Everything went well, changes are saved } catch (error) { await trx.rollback(); // Something failed, undo everything }

Las bases de datos relacionales como PostgreSQL garantizan propiedades ACID (Atomicidad, Consistencia, Aislamiento, Durabilidad). En criollo: que las operaciones se hagan completas o no se hagan (atomicidad), que los datos queden en un estado válido (consistencia), que dos operaciones al mismo tiempo no se pisen (aislamiento), y que una vez guardado, el dato no se pierda (durabilidad).

Backups: el plan B

La persistencia no es solo guardar datos, sino también protegerlos. Los backups (copias de seguridad) son esenciales. Las estrategias más comunes son:

  • Backup completo: Copia de toda la base de datos. Simple pero puede ser lento si es grande.
  • Backup incremental: Solo copia lo que cambió desde el último backup. Más rápido y eficiente.
  • Replicación: Mantener una copia sincronizada en otro servidor en tiempo real.

La regla de oro es la regla 3-2-1: tener 3 copias de tus datos, en 2 tipos de almacenamiento diferentes, con 1 copia fuera del sitio (por ejemplo, en otra región de la nube).

Cuándo y dónde persistir

No todo necesita persistirse, y elegir dónde hacerlo importa. Los datos críticos del negocio van a una base de datos robusta. Archivos grandes como imágenes o videos van a un servicio de almacenamiento como S3. Datos temporales que necesitás que sean rápidos pueden ir a un cache como Redis. Y las preferencias del usuario en el frontend pueden ir tranquilamente en localStorage. La clave es entender la naturaleza de cada dato y elegir el tipo de almacenamiento que mejor se ajuste.