Saltar al contenido principal

Acceso a bases de datos en Node.js

Node.js permite conectarse a bases de datos relacionales como MySQL o PostgreSQL mediante paquetes específicos. Esto es fundamental para aplicaciones que requieren persistencia de datos, múltiples usuarios y operaciones complejas.

En este apartado usaremos MySQL como ejemplo, con el paquete mysql2, que soporta promesas y consultas preparadas, facilitando la integración con código asíncrono moderno.

Instalación del paquete

npm install mysql2

Configuración y conexión usando ES Modules

import mysql from 'mysql2/promise';

const conexion = await mysql.createConnection({
host: 'localhost',
user: 'usuario',
password: 'clave',
database: 'miBD'
});

console.log('Conexión establecida con la base de datos');
Versión con asincronía

Se usa mysql2/promise para poder aprovechar async/await.

Consultas básicas

SELECT

const [filas] = await conexion.execute('SELECT id, nombre, email FROM usuarios');
filas.forEach(usuario => {
console.log(`${usuario.id} - ${usuario.nombre} - ${usuario.email}`);
});

INSERT

const nombre = 'Ana';
const email = 'ana@example.com';

const [resultado] = await conexion.execute(
'INSERT INTO usuarios (nombre, email) VALUES (?, ?)',
[nombre, email]
);

console.log('Usuario insertado con ID:', resultado.insertId);

UPDATE

const [resultado] = await conexion.execute(
'UPDATE usuarios SET email = ? WHERE id = ?',
['nuevo_email@example.com', 2]
);

console.log('Número de filas actualizadas:', resultado.affectedRows);

DELETE

const [resultado] = await conexion.execute(
'DELETE FROM usuarios WHERE id = ?',
[3]
);

console.log('Número de filas eliminadas:', resultado.affectedRows);

Transacciones

Las transacciones permiten agrupar varias operaciones y asegurar que todas se ejecuten correctamente o ninguna en caso de error:

try {
await conexion.beginTransaction();

await conexion.execute(
'UPDATE cuentas SET saldo = saldo - ? WHERE id = ?',
[100, 1]
);

await conexion.execute(
'UPDATE cuentas SET saldo = saldo + ? WHERE id = ?',
[100, 2]
);

await conexion.commit();
console.log('Transferencia realizada correctamente');
} catch (err) {
await conexion.rollback();
console.error('Error en la transacción:', err);
}

Buenas prácticas

  • Usar consultas parametrizadas para prevenir inyección SQL.
  • Manejar errores con try/catch cuando se usan async/await.
  • Cerrar la conexión cuando ya no se necesite:
    await conexion.end();
  • Para operaciones frecuentes o en aplicaciones de alto tráfico, usar pools de conexiones:
    const pool = mysql.createPool({
    host: 'localhost',
    user: 'usuario',
    password: 'clave',
    database: 'miBD',
    waitForConnections: true,
    connectionLimit: 10,
    queueLimit: 0
    });

    const [filas] = await pool.execute('SELECT * FROM usuarios');