Importar y Exportar Bases de Datos MySQL Usando la Línea de Comandos
Dominar las operaciones de importación y exportación de bases de datos MySQL desde la línea de comandos es una habilidad imprescindible para cualquier administrador de bases de datos o ingeniero de backend. La utilidad `mysqldump` exporta una base de datos a un archivo `.sql` portátil que contiene todas las instrucciones DDL y DML necesarias para reconstruir completamente el esquema y los datos, mientras que el comando cliente `mysql` se encarga del proceso inverso: transmitir ese archivo de vuelta a una instancia MySQL en ejecución.
Esta guía cubre todos los escenarios prácticos: exportaciones de una sola base de datos, volcados de múltiples bases de datos, copias de seguridad solo de estructura, transferencias comprimidas, manejo de conjuntos de caracteres y flujos de trabajo de importación seguros, incluidos los casos extremos que causan corrupción silenciosa de datos o fallos en las restauraciones en entornos de producción.
Requisitos previos
Antes de ejecutar cualquier comando en esta guía, verifique lo siguiente:
- MySQL Server (5.7, 8.0 o 8.4) está instalado y el proceso `mysqld` está en ejecución
- Los binarios `mysqldump` y `mysql` están en el `PATH` de su sistema (confirme con `which mysqldump`)
- Dispone de una cuenta MySQL con al menos los privilegios `SELECT`, `LOCK TABLES`, `SHOW VIEW` y `TRIGGER` para exportar; `CREATE`, `INSERT`, `ALTER` y `DROP` para importar
- Existe espacio en disco suficiente en el destino: un volcado comprimido puede expandirse entre 5 y 10 veces al importarse
- Tiene acceso shell al servidor (terminal local, SSH o un entorno de Alojamiento VPS administrado)
Exportación de bases de datos con mysqldump
`mysqldump` es la herramienta de copia de seguridad lógica canónica incluida con MySQL. Serializa los objetos de la base de datos en un script SQL legible por humanos. A diferencia de las herramientas de copia de seguridad física como Percona XtraBackup, `mysqldump` es independiente del motor de almacenamiento y funciona en distintas versiones de MySQL e incluso en bifurcaciones de MariaDB.
1. Exportar una sola base de datos
“`bash
mysqldump -u [username] -p [database_name] > [filename].sql
“`
Desglose de parámetros:
- `-u [username]` — Cuenta MySQL utilizada para la conexión
- `-p` — Activa una solicitud de contraseña interactiva (nunca pase la contraseña en línea como `-p[password]` en sistemas compartidos; es visible en la salida de `ps aux`)
- `[database_name]` — Esquema de destino a exportar
- `> [filename].sql` — Redirige la salida estándar al archivo de salida
Ejemplo:
“`bash
mysqldump -u root -p mydatabase > mydatabase_backup.sql
“`
Esto produce un archivo que contiene instrucciones `CREATE TABLE`, `INSERT` y `ALTER TABLE` suficientes para recrear `mydatabase` desde cero.
Caso extremo crítico: De forma predeterminada, `mysqldump` adquiere un bloqueo de lectura global (`FLUSH TABLES WITH READ LOCK`) al inicio del volcado. En servidores InnoDB con alto tráfico, use `–single-transaction` en su lugar para tomar una instantánea consistente sin bloquear las escrituras:
“`bash
mysqldump -u root -p –single-transaction mydatabase > mydatabase_backup.sql
“`
`–single-transaction` solo funciona de manera confiable con tablas InnoDB. Si su base de datos contiene tablas MyISAM, el bloqueo es inevitable.
2. Exportar múltiples bases de datos
“`bash
mysqldump -u [username] -p –databases db1 db2 > multiple_databases_backup.sql
“`
El indicador `–databases` indica a `mysqldump` que incluya instrucciones `CREATE DATABASE` y `USE` en la salida, haciendo que el volcado sea autónomo. Sin este indicador, esas instrucciones se omiten y el volcado asume que una base de datos de destino ya está seleccionada en el momento de la importación.
Ejemplo:
“`bash
mysqldump -u root -p –databases db1 db2 > multiple_databases_backup.sql
“`
3. Exportar todas las bases de datos
“`bash
mysqldump -u root -p –all-databases > all_databases_backup.sql
“`
Esto exporta todos los esquemas a los que puede acceder el usuario que se conecta, incluidas las bases de datos del sistema `mysql`, `information_schema` y `performance_schema`. Evite importar bases de datos del sistema entre versiones principales de MySQL: el esquema de la tabla de privilegios cambió significativamente entre MySQL 5.7 y 8.0, y la importación del esquema antiguo de `mysql` en una instancia nueva de 8.0 corromperá la autenticación.
Para excluir los esquemas del sistema:
“`bash
mysqldump -u root -p –all-databases
–ignore-table=mysql.user
–ignore-table=mysql.db
> all_user_databases_backup.sql
“`
4. Exportar solo la estructura de la tabla (sin datos)
“`bash
mysqldump -u root -p –no-data mydatabase > structure_only.sql
“`
Esto es muy útil para el control de versiones de esquemas, revisiones de código o la puesta en marcha de un entorno de pruebas en blanco. La salida contiene únicamente DDL como `CREATE TABLE`, `CREATE VIEW`, `CREATE PROCEDURE` y similares, sin filas `INSERT`.
5. Exportar tablas específicas
“`bash
mysqldump -u root -p mydatabase table1 table2 > tables_backup.sql
“`
Tenga en cuenta que al exportar tablas específicas de esta manera, `mysqldump` no incluye instrucciones `CREATE DATABASE` ni `USE`. Debe asegurarse de que la base de datos de destino exista antes de importar.
6. Exportar con procedimientos almacenados, disparadores y eventos
De forma predeterminada, `mysqldump` incluye disparadores pero omite procedimientos almacenados, funciones y eventos programados. Para una copia de seguridad completa de la aplicación:
“`bash
mysqldump -u root -p
–routines
–triggers
–events
–single-transaction
mydatabase > full_backup.sql
“`
Olvidar `–routines` es una de las causas más comunes de restauraciones de aplicaciones fallidas: el esquema y los datos están presentes, pero falta la lógica de negocio.
7. Exportación comprimida
Canalice la salida directamente a través de `gzip` para reducir el tamaño del archivo entre un 60 y un 80 %:
“`bash
mysqldump -u root -p mydatabase | gzip > mydatabase_backup.sql.gz
“`
Para la máxima compresión en bases de datos grandes (a costa de tiempo de CPU):
“`bash
mysqldump -u root -p mydatabase | gzip -9 > mydatabase_backup.sql.gz
“`
Importación de bases de datos con el cliente mysql
El cliente de línea de comandos `mysql` acepta un archivo SQL mediante redirección de entrada estándar y ejecuta cada instrucción secuencialmente contra el servidor de destino.
1. Importar a una base de datos existente
“`bash
mysql -u [username] -p [database_name] < [filename].sql
“`
Ejemplo:
“`bash
mysql -u root -p mydatabase < mydatabase_backup.sql
“`
Importante: Si el archivo `.sql` fue exportado con `–databases` o `–all-databases`, ya contiene directivas `CREATE DATABASE` y `USE`. En ese caso, no especifique un nombre de base de datos en la línea de comandos, ya que hacerlo genera un conflicto:
“`bash
mysql -u root -p < all_databases_backup.sql
“`
2. Importar a una nueva base de datos
La base de datos de destino debe existir antes de poder importar en ella. MySQL no la creará automáticamente a partir de un volcado de tabla básico.
Paso 1 — Crear la base de datos:
“`bash
mysql -u root -p -e "CREATE DATABASE newdatabase CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;"
“`
Paso 2 — Importar el volcado:
“`bash
mysql -u root -p newdatabase < mydatabase_backup.sql
“`
Especifique siempre el conjunto de caracteres y la intercalación explícitamente al crear la base de datos. Depender de los valores predeterminados del servidor es una fuente frecuente de discrepancias de codificación, especialmente al migrar entre servidores con diferentes configuraciones de `character_set_server`.
3. Importar un volcado comprimido
“`bash
gunzip < mydatabase_backup.sql.gz | mysql -u root -p mydatabase
“`
O usando `zcat` (equivalente en la mayoría de las distribuciones Linux):
“`bash
zcat mydatabase_backup.sql.gz | mysql -u root -p mydatabase
“`
4. Importar con monitoreo de progreso
Para volcados grandes, el cliente estándar `mysql` no proporciona retroalimentación. Use `pv` (visor de tuberías) para mostrar una barra de progreso en tiempo real:
“`bash
pv mydatabase_backup.sql | mysql -u root -p mydatabase
“`
Instale `pv` con `apt install pv` o `yum install pv`. En un Servidor Dedicado que gestiona bases de datos de producción de varios gigabytes, esta visibilidad es operativamente crítica.
mysqldump vs. métodos alternativos de copia de seguridad
| Característica | mysqldump | mysqlpump | MySQL Shell (util.dumpInstance) | Percona XtraBackup |
|---|
| — | — | — | — | — |
|---|
| Tipo de copia de seguridad | Lógica (SQL) | Lógica (SQL) | Lógica (JSON/SQL) | Física (binaria) |
|---|
| Paralelismo | Un solo hilo | Multihilo | Multihilo | Multihilo |
|---|
| Copia de seguridad en caliente de InnoDB | Con `–single-transaction` | Con `–single-transaction` | Sí | Sí |
|---|
| Formato de salida | SQL plano | SQL plano | Archivos fragmentados | Archivos InnoDB sin procesar |
|---|
| Velocidad de restauración | Lenta (SQL secuencial) | Moderada | Rápida | Muy rápida |
|---|
| Portabilidad entre versiones | Excelente | Buena | Buena | Solo la misma versión principal |
|---|
| Incluido en MySQL | Sí | Sí (5.7.8+) | Instalación separada | Terceros |
|---|
| Mejor caso de uso | Portabilidad, bases de datos pequeñas y medianas | Volcados paralelos | Esquemas en la nube o de gran tamaño | Bases de datos de producción grandes |
|---|
Para entornos que ejecutan múltiples bases de datos de producción en un VPS con cPanel administrado, `mysqldump` sigue siendo la opción con mayor compatibilidad universal debido a su compatibilidad y simplicidad.
Configuración avanzada y casos extremos
Manejo correcto de conjuntos de caracteres
Las discrepancias en los conjuntos de caracteres son responsables de una proporción desproporcionada de importaciones corruptas. El enfoque más seguro es ser explícito en cada etapa:
“`bash
mysqldump -u root -p
–default-character-set=utf8mb4
mydatabase > mydatabase_backup.sql
“`
“`bash
mysql -u root -p
–default-character-set=utf8mb4
mydatabase < mydatabase_backup.sql
“`
Nota: `utf8` en MySQL es un subconjunto de 3 bytes que no puede almacenar caracteres Unicode de 4 bytes (emojis, ciertos ideogramas CJK). Use siempre `utf8mb4` para nuevas bases de datos.
Aceleración de importaciones grandes
De forma predeterminada, MySQL realiza una confirmación completa después de cada instrucción `INSERT` en el volcado. Para conjuntos de datos grandes, esto es extremadamente lento. Agregue lo siguiente al inicio de su sesión de importación:
“`bash
mysql -u root -p mydatabase <<EOF
SET foreign_key_checks = 0;
SET unique_checks = 0;
SET autocommit = 0;
SOURCE /path/to/mydatabase_backup.sql;
COMMIT;
SET foreign_key_checks = 1;
SET unique_checks = 1;
EOF
“`
Alternativamente, exporte con `–extended-insert` (habilitado de forma predeterminada) y `–disable-keys` para agrupar inserciones y diferir la reconstrucción de índices hasta después de la carga de datos.
Automatización de copias de seguridad con Cron
Una entrada de copia de seguridad automatizada de nivel de producción en `/etc/cron.d/mysql-backup`:
“`bash
0 2 * * * root mysqldump -u backup_user -p'StrongPass'
–single-transaction –routines –triggers –events
mydatabase | gzip > /backups/mydatabase_$(date +%F).sql.gz
“`
Use un usuario MySQL dedicado con los privilegios mínimos requeridos en lugar de `root`. Créelo con:
“`sql
CREATE USER 'backup_user'@'localhost' IDENTIFIED BY 'StrongPass';
GRANT SELECT, LOCK TABLES, SHOW VIEW, TRIGGER, EVENT ON *.* TO 'backup_user'@'localhost';
FLUSH PRIVILEGES;
“`
Protección de credenciales con .my.cnf
Pasar contraseñas en la línea de comandos las expone en el historial del shell y en las listas de procesos. Almacene las credenciales en `~/.my.cnf`:
“`ini
[client]
user=root
password=YourSecurePassword
“`
Establezca los permisos de inmediato:
“`bash
chmod 600 ~/.my.cnf
“`
Con esto configurado, todos los comandos `mysqldump` y `mysql` recogen las credenciales automáticamente sin necesidad de los indicadores `-u` y `-p`.
Exportación de base de datos remota
Para volcar una base de datos desde un servidor MySQL remoto:
“`bash
mysqldump -h remote.server.com -P 3306 -u remoteuser -p remotedatabase > remote_backup.sql
“`
Asegúrese de que la instancia MySQL remota permita conexiones desde su dirección IP y que el puerto 3306 esté abierto en el firewall. Para transferencias cifradas, use un túnel SSH:
“`bash
ssh -L 3307:127.0.0.1:3306 user@remote.server.com -N &
mysqldump -h 127.0.0.1 -P 3307 -u remoteuser -p remotedatabase > remote_backup.sql
“`
Matriz de decisión práctica
| Escenario | Comando recomendado |
|---|
| — | — |
|---|
| Copia de seguridad completa, solo InnoDB, sin tiempo de inactividad | `mysqldump –single-transaction –routines –triggers –events` |
|---|
| Migración de esquema a nuevo servidor | `mysqldump –no-data` + recrear base de datos + importar |
|---|
| Mover una sola base de datos entre servidores | `mysqldump db | gzip | ssh user@dest "gunzip | mysql db"` |
|---|
| Hacer copia de seguridad de todas las bases de datos, excluir esquemas del sistema | `–all-databases` + `–ignore-table` para tablas del sistema |
|---|
| Restauración rápida de volcado grande | Deshabilitar `foreign_key_checks`, `unique_checks`, `autocommit` |
|---|
| Copia de seguridad automática nocturna | Cron + usuario de copia de seguridad dedicado + credenciales `.my.cnf` |
|---|
| Verificar integridad de la copia de seguridad | Importar a una base de datos de prueba y ejecutar `SHOW TABLE STATUS` |
|---|
Conclusiones técnicas clave
- Use siempre `–single-transaction` para bases de datos InnoDB para evitar bloquear las escrituras de la aplicación durante la exportación
- Especifique siempre `utf8mb4` explícitamente: nunca dependa de las suposiciones predeterminadas del conjunto de caracteres del servidor
- Incluya `–routines`, `–triggers` y `–events` en cada copia de seguridad completa de la aplicación o arriesgará perder la lógica de negocio
- Nunca importe tablas de esquemas del sistema (`mysql.*`) entre versiones principales de MySQL
- Almacene las credenciales en `~/.my.cnf` con `chmod 600`: nunca pase contraseñas como argumentos en línea
- Para bases de datos que superen los 10 GB, evalúe `mysqlpump` o las utilidades de volcado paralelo de MySQL Shell, ya que `mysqldump` se convertirá en un cuello de botella
- Verifique cada copia de seguridad realizando una restauración de prueba en un entorno aislado antes de confiar en ella para la recuperación ante desastres
- Al alojar múltiples bases de datos de clientes, aísle los entornos usando Paneles de Control VPS separados para evitar el acceso entre inquilinos durante las operaciones de restauración
- Complemente su estrategia de copia de seguridad de bases de datos con un Certificado SSL válido en cualquier capa de aplicación web que se conecte a MySQL para evitar la interceptación de credenciales en tránsito
Preguntas frecuentes
¿Cuál es la diferencia entre mysqldump y mysqlpump?
`mysqldump` es de un solo hilo y produce un único archivo SQL: confiable y universalmente compatible. `mysqlpump`, introducido en MySQL 5.7.8, admite la exportación paralela de múltiples bases de datos y tablas simultáneamente, lo que reduce significativamente el tiempo de volcado en servidores multinúcleo. Sin embargo, `mysqlpump` tiene problemas conocidos con las copias de seguridad consistentes de bases de datos con motores mixtos y es menos adecuado para migraciones entre versiones.
¿Puedo importar un volcado de MySQL 5.7 en MySQL 8.0?
Sí, con advertencias. Los datos de usuario y los esquemas de aplicaciones se importan correctamente. Sin embargo, nunca importe la base de datos del sistema `mysql` directamente: el complemento de autenticación cambió de `mysql_native_password` a `caching_sha2_password` en la versión 8.0, y la importación de tablas de privilegios antiguas romperá la autenticación. Vuelva a crear los usuarios manualmente usando instrucciones `CREATE USER` y `GRANT`.
¿Por qué falla mi importación con "ERROR 1005: Can't create table" debido a restricciones de clave foránea?
Esto ocurre cuando las tablas se importan en un orden que viola las dependencias de clave foránea. La solución es anteponer `SET foreign_key_checks = 0;` a su sesión de importación y agregar `SET foreign_key_checks = 1;` al finalizar. Alternativamente, exporte con `–single-transaction`, que preserva la integridad referencial en el propio archivo de volcado.
¿Cómo exporto solo los datos sin las instrucciones CREATE TABLE?
Use el indicador `–no-create-info`: `mysqldump -u root -p –no-create-info mydatabase > data_only.sql`. Esto es útil cuando necesita recargar datos en un esquema existente sin alterar su estructura.
¿Cuál es la forma más segura de transferir un volcado MySQL entre dos servidores remotos?
Canalice el volcado directamente a través de SSH sin escribir un archivo intermedio en disco: `mysqldump -u root -p sourcedb | ssh user@destination.server "mysql -u root -p targetdb"`. Esto es más rápido y seguro que copiar un archivo `.sql` en texto plano, especialmente cuando se opera en un entorno de Alojamiento Web Compartido donde las cuotas de disco son una limitación.
