
Objetivos del Laboratorio
Objetivo general: Implementar un clúster de alta disponibilidad de MySQL 8.0 en Debian 13.4 utilizando DRBD para replicación de almacenamiento a nivel de bloque y configurando simultáneamente la replicación nativa de MySQL (Primary‑Replica). El entorno final constará de dos nodos (nodo‑a y nodo‑b) capaces de garantizar continuidad del servicio de base de datos, replicación síncrona de almacenamiento y sincronización a nivel de transacciones SQL.
Objetivos específicos:
| # | Objetivo | Alcance |
|---|---|---|
| 1 | Comprender qué es MySQL | Definición, características clave, modelo relacional |
| 2 | Identificar la estructura de archivos de MySQL | datadir, InnoDB, logs, socket, configuración |
| 3 | Instalar MySQL 8.0 en Debian 13.4 | Repositorio oficial Oracle, configuración segura |
| 4 | Integrar MySQL en clúster HA | DRBD + Pacemaker/Corosync, datadir sobre volumen replicado |
| 5 | Configurar replicación nativa MySQL | Primary‑Replica, usuario de replicación, binlog, verificación |
| 6 | Validar y documentar pruebas | Failover, integridad de datos, problemas comunes |
Nota sobre las referencias del laboratorio previo: Las prácticas publicadas en
dsantana.uas.edu.mx—sobre implementación de clúster HA, DRBD en Debian 13.4 y clúster de alta disponibilidad en Debian 13— no pudieron consultarse directamente durante la investigación. La presente guía se construye sobre documentación oficial de MySQL (Oracle), guías técnicas verificadas de instalación en Debian, y referencias de configuración de Pacemaker/Corosync/DRBD, alineándose con los principios y arquitectura descritos en dichas prácticas previas.

1. ¿Qué es MySQL?
MySQL es un sistema de gestión de bases de datos relacionales (RDBMS) de código abierto que se utiliza para almacenar y gestionar datos. Su fiabilidad, rendimiento, escalabilidad y facilidad de uso lo han convertido en una opción popular para desarrolladores en aplicaciones de alto tráfico como Facebook, Netflix, Uber, Airbnb, Shopify y Booking.com. En 2024, MySQL se clasifica como la segunda base de datos más popular en general, solo superada por Oracle Database según DB‑Engines, y es el RDBMS de código abierto más popular del mundo.
MySQL utiliza el lenguaje SQL (Structured Query Language) para recuperar, actualizar, suprimir y manipular datos en bases de datos relacionales. Se pronuncia oficialmente «My es‑kiu‑el». Como base de datos relacional, almacena datos en tablas de filas y columnas organizadas en esquemas, donde un esquema define cómo se organizan y almacenan los datos y describe la relación entre varias tablas. Recientemente, Oracle ha añadido soporte para el tipo de datos JSON y vectores, ampliando su versatilidad.
Características fundamentales:
- Transacciones ACID: Soporta atomicidad, consistencia, aislamiento y durabilidad, garantizando que las modificaciones de datos se realicen de manera coherente y fiable, incluso en caso de un fallo del sistema.
- Código abierto: Disponible bajo GNU General Public License (GPL), lo que permite descargarlo y usarlo sin costo. También existe una versión con licencia comercial para quienes deseen incorporar código MySQL en aplicaciones propietarias.
- Rendimiento y escalabilidad: La arquitectura de replicación nativa de MySQL permite a organizaciones como Facebook escalar aplicaciones para admitir miles de millones de usuarios. MySQL puede manejar un alto volumen de conexiones simultáneas.
- Alta disponibilidad: Ofrece tecnologías de replicación nativas e integradas que permiten lograr un objetivo de punto de recuperación cero y un objetivo de tiempo de recuperación de cero segundos mediante conmutación automática por error.
- Arquitectura cliente/servidor: MySQL Database es un sistema que consta de un servidor SQL multihilo con diferentes backends, varios programas y bibliotecas cliente, herramientas administrativas y una amplia variedad de APIs.
- Compatibilidad: Amplia compatibilidad con plataformas tecnológicas y lenguajes de programación, incluyendo Java, Python, PHP y JavaScript. Admite replicación entre versiones (p. ej., MySQL 5.7 a MySQL 8.0).
- Seguridad: En su edición Enterprise incluye autenticación/autorización avanzada, cifrado transparente de datos, auditoría, enmascaramiento de datos y firewall de base de datos.
2. Estructura del Sistema de Archivos y Componentes de MySQL
2.1 Directorio de datos (datadir)
El datadir es la carpeta principal donde el servidor MySQL almacena todos los archivos relacionados con las bases de datos. En instalaciones desde repositorios (apt, yum) en Linux, la ubicación más común es /var/lib/mysql/. Este valor está definido por la variable del sistema data_dir, cuyo valor por defecto es /var/lib/mysql. Para consultar el datadir activo, puede ejecutarse dentro de MySQL la sentencia SHOW VARIABLES LIKE 'datadir';.
Dentro del datadir se encuentra:
- Un subdirectorio por cada base de datos (con nombre homónimo), conteniendo los archivos de tablas del motor correspondiente.
- Archivos globales del motor InnoDB (espacio de tablas compartido, logs de recuperación).
- Archivos de definición de estructura de tablas.
2.2 Motor de almacenamiento InnoDB
InnoDB es el motor de almacenamiento predeterminado en MySQL 8.0 y actúa como la capa intermedia entre el almacenamiento y el servidor MySQL, almacenando los datos en las unidades de disco. Su funcionamiento de E/S se clasifica en dos tipos: I/O de archivo aleatorio (archivos de datos) y E/S de archivo secuencial (registros de recuperación y binarios).
Componentes clave de InnoDB en el datadir:
| Componente | Descripción |
|---|---|
Espacio de tablas compartido (ibdata1) | Contiene metadatos de InnoDB y datos de tablas que no usan file‑per‑table. Con innodb_file_per_table activado (predeterminado en MySQL 8), cada tabla se almacena en archivos .ibd independientes. |
| Logs de recuperación (redo logs) | Registros transaccionales escritos secuencialmente para garantizar la recuperación tras fallos. |
| Buffer de doble escritura | InnoDB escribe páginas primero en un buffer y luego en sus posiciones correctas en los archivos de datos, evitando la corrupción de páginas si se produce un fallo de alimentación durante la escritura. |
| Buffer de inserción | Reduce operaciones de E/S aleatorias fusionando escrituras en índices secundarios no únicos. |
| Segmentos de deshacer (undo) | Registran imágenes anteriores de los datos para la concurrencia multiversión (MVCC). |
2.3 Archivos de registro (logs)
MySQL dispone de cuatro tipos principales de archivos de log:
| Tipo de log | Descripción | Ruta típica (Debian) | Activado por defecto |
|---|---|---|---|
| Registro de errores | Registra problemas al iniciar, ejecutar o parar mysqld | /var/log/mysql/error.log | Sí |
| Registro de consultas generales | Registra todas las conexiones y sentencias ejecutadas | datadir/<hostname>.log | No |
| Registro binario (binlog) | Registra todas las sentencias que cambian datos; utilizado en la replicación | datadir/mysql-bin.* (si se activa log_bin) | No |
| Registro de consultas lentas | Registra sentencias que exceden el tiempo definido por long_query_time (predeterminado: 10 segundos) | datadir/<hostname>-slow.log | No |
Por defecto, todos los archivos de log se crean en el directorio de datos, aunque distribuciones Debian/Ubuntu suelen redirigir el log de errores a /var/log/mysql/error.log mediante la variable log_error.
El registro binario merece atención especial para este laboratorio: es la base de la replicación nativa de MySQL. Debe habilitarse configurando log_bin en el archivo de configuración. Cada archivo binlog se escribe secuencialmente y contiene las operaciones de escritura (INSERT, UPDATE, DELETE). Los binlogs cumplen tres funciones principales: restauración punto en el tiempo, replicación entre servidores, y auditoría de seguridad.
2.4 Archivo de socket Unix
El archivo mysqld.sock es un punto final de comunicación que permite que el servidor MySQL y las aplicaciones cliente en la misma máquina se comuniquen de manera local sin pasar por la red TCP/IP. En sistemas Debian/Ubuntu, este socket se encuentra normalmente en /var/run/mysqld/mysqld.sock. Se configura mediante la directiva socket en el archivo my.cnf.
2.5 Archivo PID y archivo de configuración
- Archivo PID (
mysqld.pid): Contiene el ID de proceso del demonio MySQL activo; se encuentra controlado por el parámetropid_filey por defecto reside en el directorio de la base de datos o en/var/run/mysqld/. - Archivo de configuración principal: En Debian/Ubuntu, el archivo es
/etc/mysql/mysql.conf.d/mysqld.cnf(incluido desde/etc/mysql/my.cnf). Aquí se definen directivas comodatadir,bind-address,socket,log_error, parámetros de InnoDB, y opciones de replicación.
2.6 Parámetros de configuración relevantes
Los parámetros de MySQL se dividen en dinámicos (modificables en tiempo de ejecución con SET) y estáticos (requieren reinicio del servicio). Algunos parámetros clave:
| Parámetro | Tipo | Descripción |
|---|---|---|
innodb_buffer_pool_size | Estático | Tamaño del buffer de datos/índices InnoDB en memoria |
log_bin | Estático | Activa registro binario para replicación |
server_id | Estático | Identificador único del servidor en topología de replicación |
bind-address | Estático | Dirección IP en la que MySQL escucha conexiones |
sync_binlog | Dinámico | Frecuencia de sincronización del binlog al disco; 1 = máxima seguridad |
2.7 Permisos y AppArmor
MySQL ejecuta bajo el usuario del sistema mysql. Todos los archivos del datadir deben pertenecer a mysql:mysql. En distribuciones Debian/Ubuntu, AppArmor confina el proceso mysqld mediante un perfil en /etc/apparmor.d/usr.sbin.mysqld. Si se cambia la ubicación del datadir (como haremos al usar DRBD), deben ajustarse las reglas de AppArmor para incluir las nuevas rutas; de lo contrario, MySQL podría no iniciar por restricciones de acceso.
3. Instalación de MySQL 8.0 en Debian 13.4
Debian incluye MariaDB por defecto en sus repositorios en lugar de MySQL. Para instalar MySQL 8 se requiere usar el repositorio oficial de MySQL de Oracle.
Prerrequisitos del laboratorio
| Elemento | Valor de ejemplo |
|---|---|
| nodo‑a (Primary) | IP: 192.168.1.101 |
| nodo‑b (Replica) | IP: 192.168.1.102 |
| Red del clúster | 192.168.1.0/24 |
| IP virtual (flotante) | 192.168.1.150 |
| Disco DRBD | /dev/sdb1 (~10 GB en cada nodo) |
| Punto de montaje DRBD | /mysql |
| SO | Debian 13.4 (Trixie) |
Las direcciones IP son ejemplos. Ajuste según su entorno. Asegúrese de que ambos nodos se resuelvan mutuamente (vía DNS o
/etc/hosts) y que los puertos 3306 (MySQL), 7789 (DRBD), 5404/5405 UDP (Corosync) y SSH estén abiertos entre ellos.
3.1 Paso a paso de instalación
Paso 1 — Actualizar el sistema e instalar dependencias.
En cada nodo:
sudo apt update
sudo apt upgrade -y
sudo apt install -y lsb-release gnupg curl
El paquete lsb-release proporciona información sobre la distribución y gnupg es necesario para verificar la autenticidad de paquetes.
Paso 2 — Habilitar el repositorio oficial de MySQL.
Descargue el paquete de configuración del repositorio MySQL APT desde la https://dev.mysql.com/downloads/repo/apt/:
curl -OL https://dev.mysql.com/get/mysql-apt-config_0.8.24-1_all.deb
sudo dpkg -i mysql-apt-config_0.8.24-1_all.deb
Durante la instalación interactiva, seleccione MySQL Server 8.0. Use las flechas del teclado para navegar y Enter para confirmar.
Nota: La versión del paquete (
0.8.24-1en este ejemplo) puede cambiar. Verifique la versión vigente en la página oficial de MySQL APT Repository.
Actualice la caché de paquetes para incluir los nuevos repositorios:
sudo apt update
Paso 3 — Instalar MySQL Server.
En ambos nodos:
sudo apt install mysql-server -y
Este comando instalará MySQL 8 junto con sus dependencias. Durante la instalación podría solicitarse configurar la contraseña del usuario root de MySQL.
Paso 4 — Asegurar la instalación.
Ejecute en cada nodo:
sudo mysql_secure_installation
Este script permite:
- Establecer una contraseña robusta para
root(si no se configuró antes). - Eliminar usuarios anónimos.
- Deshabilitar el acceso remoto para
root. - Eliminar la base de datos de prueba y recargar privilegios.
Paso 5 — Verificar el estado del servicio.
sudo systemctl status mysql
Si el servicio está activo, podrá conectarse con:
mysql -u root -p
Para habilitarlo al arranque del sistema:
sudo systemctl enable mysql
3.2 Ajustes de configuración para clúster y replicación
Edite /etc/mysql/mysql.conf.d/mysqld.cnf en ambos nodos:
En nodo‑a (Primary):
[mysqld]
bind-address = 0.0.0.0
server-id = 1
log_bin = mysql-bin
binlog_format = ROW
expire_logs_days = 7
bind-address = 0.0.0.0permite conexiones desde cualquier interfaz de red.server-iddebe ser único para cada servidor en la topología de replicación.log_binactiva el registro binario con nombre basemysql-bin.binlog_format = ROWregistra modificaciones a nivel de fila (recomendado para replicación).
En nodo‑b (Replica):
[mysqld]
bind-address = 0.0.0.0
server-id = 2
log_bin = mysql-bin
relay_log = mysql-relay-bin
read_only = 1
relay_lognombra los archivos de relay log (registros de relevo) en la réplica.read_only = 1impide escrituras por usuarios sin privilegio SUPER, protegiendo la integridad de la replicación.
Directiva datadir para DRBD (ambos nodos): Se aplicará en la sección 4, una vez configurado el volumen. El cambio será:
datadir = /mysql
log-error = /mysql/mysqld.err
Esto redirige el almacenamiento de datos al punto de montaje del volumen DRBD, como se muestra en configuraciones de entornos similares.
Firewall: Abra el puerto 3306 en nodo‑a para la conexión del Replica:
sudo ufw allow from 192.168.1.102 to any port 3306
4. Implementación del Clúster de Alta Disponibilidad y DRBD
Diagrama lógico (descripción textual)
┌─────────────┐ ┌─────────────┐
│ nodo-a │◄──DRBD──►│ nodo-b │
│ 192.168.1.101│ (TCP │ 192.168.1.102│
│ │ 7789) │ │
│ /dev/sdb1 │ │ /dev/sdb1 │
│ /dev/drbd0 │ │ /dev/drbd0 │
│ mount:/mysql│ │ (no montado)│
│ MySQL ✔ │ │ MySQL ✗ │
│ VIP: .150 │ │ │
└──────┬──────┘ └──────┬──────┘
│ Corosync/Pacemaker │
└────────────────────────┘
- Solo el nodo activo (DRBD Primary) monta
/dev/drbd0en/mysqly ejecuta MySQL. - Pacemaker orquesta: promoción de DRBD → montaje de FS → asignación de IP virtual → arranque de MySQL.
- Ante falla, los recursos migran automáticamente al nodo pasivo.
4.1 Instalación de paquetes
En ambos nodos:
sudo apt install -y drbd-utils pacemaker corosync crmsh pcs
Esto instala DRBD y la pila de alta disponibilidad. En Debian/Ubuntu, los paquetes se instalan con apt:
sudo apt-get install -y pacemaker corosync pcs fence-agents-all
4.2 Configuración de DRBD
Paso 1 — Definir el recurso DRBD.
Cree /etc/drbd.d/mysqldata.res en ambos nodos:
resource mysqldata {
protocol C;
meta-disk internal;
device /dev/drbd0;
disk /dev/sdb1;
on nodo-a {
address 192.168.1.101:7789;
}
on nodo-b {
address 192.168.1.102:7789;
}
}
- protocol C = replicación síncrona (la más segura; el Primary confirma la escritura solo cuando el Secondary ha recibido el dato).
- meta-disk internal = los metadatos se almacenan al final de la misma partición.
- El recurso DRBD en la referencia de CentOS sigue una estructura equivalente con
device /dev/drbd0,diskyaddresspor nodo.
Paso 2 — Crear metadatos e iniciar DRBD.
En ambos nodos:
sudo drbdadm create-md mysqldata
sudo modprobe drbd
sudo drbdadm up mysqldata
Paso 3 — Designar Primary inicial y sincronizar.
En nodo-a:
sudo drbdadm primary –force mysqldata
Verificar estado de sincronización:
cat /proc/drbd
Espere hasta ver cs:Connected y UpToDate/UpToDate en ambos nodos.
Paso 4 — Formatear y montar el volumen en nodo‑a.
sudo mkfs.ext4 /dev/drbd0 -L mysqlstore
sudo mkdir -p /mysql
sudo mount /dev/drbd0 /mysql
No agregue esta entrada en
/etc/fstabcon montaje automático. Pacemaker gestionará el montaje.
4.3 Migración del datadir de MySQL al volumen DRBD
Paso 5 — Detener MySQL y copiar datos.
En ambos nodos, detenga MySQL:
sudo systemctl stop mysql
sudo systemctl disable mysql # Evitar arranque automático; Pacemaker lo controlará
En nodo‑a (donde /mysql está montado):
sudo cp -a /var/lib/mysql/. /mysql/
sudo chown -R mysql:mysql /mysql
Paso 6 — Ajustar AppArmor.
Edite /etc/apparmor.d/usr.sbin.mysqld y agregue: [wiki.cifpr…lfoucha.es]
/mysql/ r,
/mysql/** rwk,
Recargue:
sudo apparmor_parser -r /etc/apparmor.d/usr.sbin.mysqld
Paso 7 — Aplicar nueva configuración de mysqld.cnf.
En ambos nodos, asegúrese de que la sección [mysqld] contenga:
datadir = /mysql
socket = /var/run/mysqld/mysqld.sock
log-error = /mysql/mysqld.err
pid-file = /var/run/mysqld/mysqld.pid
Verificación rápida (opcional, solo en nodo‑a):
sudo systemctl start mysql
mysql -u root -p -e «SHOW DATABASES;»
sudo systemctl stop mysql
4.4 Configuración de Corosync
Paso 8 — Crear /etc/corosync/corosync.conf (mismo contenido en ambos nodos):
totem {
version: 2
cluster_name: mysqlcluster
transport: udpu
interface {
ringnumber: 0
bindnetaddr: 192.168.1.0
mcastport: 5405
}
}
nodelist {
node {
ring0_addr: nodo-a
nodeid: 1
}
node {
ring0_addr: nodo-b
nodeid: 2
}
}
quorum {
provider: corosync_votequorum
two_node: 1
}
logging {
to_syslog: yes
}
Genere la clave de autenticación en un nodo y cópiela al otro:
sudo corosync-keygen
sudo scp /etc/corosync/authkey nodo-b:/etc/corosync/
4.5 Configuración de Pacemaker y recursos
Paso 9 — Iniciar servicios de clúster.
En ambos nodos: [linuxmind.dev]
sudo systemctl enable corosync pacemaker
sudo systemctl start corosync pacemaker
Establecer contraseña del usuario hacluster:
sudo passwd hacluster
Autenticar nodos (usando pcs): [linuxmind.dev]
sudo pcs cluster auth nodo-a nodo-b -u hacluster -p <contraseña>
Verificar estado:
sudo pcs status
Debería mostrar dos nodos online.
Paso 10 — Crear recursos del clúster.
# 1. Recurso DRBD (Master/Slave)
sudo pcs resource create res_drbd_mysql ocf:linbit:drbd \
drbd_resource="mysqldata" \
op monitor interval="15s" role="Master" \
op monitor interval="30s" role="Slave"
sudo pcs resource promotable res_drbd_mysql \
promoted-max=1 promoted-node-max=1 \
clone-max=2 clone-node-max=1 notify=true
# 2. Recurso Filesystem
sudo pcs resource create res_fs_mysql ocf:heartbeat:Filesystem \
device="/dev/drbd0" directory="/mysql" fstype="ext4" \
op start timeout="20s" op stop timeout="20s"
# 3. Recurso IP Virtual
sudo pcs resource create res_ip_mysql ocf:heartbeat:IPaddr2 \
ip="192.168.1.150" cidr_netmask="24" nic="eth0" \
op monitor interval="30s"
# 4. Recurso MySQL
sudo pcs resource create res_mysql ocf:heartbeat:mysql \
binary="/usr/sbin/mysqld_safe" \
config="/etc/mysql/my.cnf" \
datadir="/mysql" user="mysql" \
op monitor interval="20s" timeout="30s"
Los tipos de agentes utilizados corresponden a los disponibles en la pila Pacemaker/DRBD:
| Tipo de Agente | Recurso | Uso |
|---|---|---|
ocf:linbit:drbd | res_drbd_mysql | Replicación de bloque |
ocf:heartbeat:Filesystem | res_fs_mysql | Montaje del FS en /mysql |
ocf:heartbeat:IPaddr2 | res_ip_mysql | IP flotante del servicio |
ocf:heartbeat:mysql | res_mysql | Control del servicio MySQL |
Paso 11 — Agrupar recursos y definir restricciones.
# Grupo: IP + FS + MySQL se mueven juntos
sudo pcs resource group add g_mysql res_ip_mysql res_fs_mysql res_mysql
# Orden: DRBD debe estar promovido antes de iniciar el grupo
sudo pcs constraint order promote res_drbd_mysql-clone then start g_mysql
# Colocación: el grupo corre en el nodo con DRBD Master
sudo pcs constraint colocation add g_mysql with Promoted res_drbd_mysql-clone INFINITY
Paso 12 — Configuración de quórum y STONITH.
# En entorno de laboratorio, puede deshabilitarse stonith (NO en producción):
sudo pcs property set stonith-enabled=false
sudo pcs property set no-quorum-policy=ignore
Advertencia: En producción, STONITH debe estar habilitado para prevenir split‑brain y acceso concurrente al dispositivo DRBD.
Paso 13 — Verificar estado del clúster.
Shell
sudo pcs status
Mostrar más líneas
La salida esperada debería mostrar:
Cluster Summary:
* 2 nodes configured
* N resource instances configured
Node List:
* Online: [ nodo-a nodo-b ]
Full List of Resources:
* Clone Set: res_drbd_mysql-clone [res_drbd_mysql] (promotable)
* Promoted: [ nodo-a ]
* Unpromoted: [ nodo-b ]
* Resource Group: g_mysql:
* res_ip_mysql (ocf::heartbeat:IPaddr2): Started nodo-a
* res_fs_mysql (ocf::heartbeat:Filesystem): Started nodo-a
* res_mysql (ocf::heartbeat:mysql): Started nodo-a
Esto confirma que:
- nodo‑a es el Master de DRBD con el FS montado, IP virtual asignada y MySQL en ejecución.
- nodo‑b es el Slave de DRBD sin recursos activos del grupo.
5. Configuración de la Replicación Nativa de MySQL (Primary‑Replica)
La replicación en MySQL implica que la base de datos de origen anota cada cambio en los datos en un archivo especial: el registro binario (binlog). La instancia de réplica crea dos subprocesos: el subproceso IO (se conecta al origen, lee eventos del binlog y los copia a un relay log local) y el subproceso SQL (lee eventos del relay log y los aplica a la réplica).
MySQL admite dos métodos de replicación:
- Basada en posición de archivo binlog: la réplica necesita el nombre del archivo binlog y la posición exacta dentro de él.
- Basada en transacciones (GTID): cada transacción recibe un identificador global único; la réplica no necesita coordenadas de binlog, facilitando cambios de topología.
En este laboratorio usaremos replicación basada en posición de binlog por su simplicidad.
Consideración sobre el escenario DRBD + Replicación
En un clúster activo‑pasivo con DRBD, normalmente solo el nodo activo ejecuta MySQL. DRBD ya garantiza la consistencia de datos en el nodo pasivo a nivel de bloque. La replicación nativa aquí se configura con fines educativos para demostrar ambas técnicas. En un entorno real, se elige típicamente una de las dos:
- DRBD/Pacemaker: failover automático, cero pérdida de datos (síncrono), pero un solo nodo activo.
- Replicación MySQL nativa: permite múltiples réplicas para lecturas distribuidas, pero es asíncrona por defecto y requiere gestión manual de roles.
Para la demostración de replicación, asumiremos que nodo‑b tiene una instancia de MySQL operativa con un datadir inicializado (puede ser una copia restaurada desde el Primary).
5.1 Verificar binlogs en el Primary (nodo‑a)
Conéctese al MySQL del nodo‑a y ejecute:
SQL
SHOW VARIABLES LIKE ‘log_bin’;
— Resultado esperado: ON
SHOW MASTER STATUS;
La respuesta indicará el archivo binlog actual y la posición. Por ejemplo:
| File | Position |
|---|---|
| mysql-bin.000001 | 154 |
Anote estos valores para configurar la réplica.
5.2 Crear usuario de replicación en el Primary
SQL
CREATE USER ‘replicador’@’192.168.1.%’ IDENTIFIED BY ‘SecretaRep!2026’;
GRANT REPLICATION SLAVE ON *.* TO ‘replicador’@’192.168.1.%’;
FLUSH PRIVILEGES;
El privilegio REPLICATION SLAVE permite al usuario actuar como Replica; se recomienda restringir el host al IP exacto de nodo‑b para mayor seguridad.
5.3 Sincronización inicial de datos
Si el Replica no tiene los datos del Primary, debe crearse un volcado y restaurarlo. Desde nodo‑a:
sudo mysqldump -u root –all-databases –master-data > /tmp/dump.sql
scp /tmp/dump.sql nodo-b:/tmp/
En nodo‑b, restaurar:
sudo mysql < /tmp/dump.sql
En nuestro escenario con DRBD, los datos ya están sincronizados a nivel de bloque, por lo que este paso puede omitirse si se ha restaurado una copia del datadir.
5.4 Configurar y activar la Replica (nodo‑b)
En MySQL de nodo‑b:
SQL
CHANGE REPLICATION SOURCE TO
SOURCE_HOST=’192.168.1.101′,
SOURCE_USER=’replicador’,
SOURCE_PASSWORD=’SecretaRep!2026′,
SOURCE_LOG_FILE=’mysql-bin.000001′,
SOURCE_LOG_POS=154;
START REPLICA;
En MySQL 8, se usa la sintaxis
SOURCE_*en lugar deMASTER_*(ambas aceptadas por compatibilidad).
5.5 Verificar estado de replicación
SQL
SHOW REPLICA STATUS\G
Campos clave a verificar:
| Campo | Valor esperado |
|---|---|
Replica_IO_Running | Yes |
Replica_SQL_Running | Yes |
Seconds_Behind_Source | 0 (o tendiendo a 0) |
Si algún campo muestra No, verifique: contraseña incorrecta, host no accesible (firewall), server-id duplicados, o binlog no habilitado en el Primary.
5.6 Prueba de replicación
En nodo‑a (Primary):
SQL
CREATE DATABASE prueba_replicacion;
USE prueba_replicacion;
CREATE TABLE test (id INT PRIMARY KEY AUTO_INCREMENT, msg VARCHAR(50));
INSERT INTO test (msg) VALUES (‘Dato desde nodo-a’);
En nodo‑b (Replica):
SQL
SELECT * FROM prueba_replicacion.test;
Debería mostrar el registro insertado en el Primary, confirmando la replicación funcional.
6. Pruebas de Funcionamiento

Ejemplo detallado de Prueba 2 — Failover:
# 1. Estado inicial: nodo-a activo
sudo pcs status | grep -A 5 «Resource Group»
# 2. Simular falla en nodo-a
sudo pcs node standby nodo-a
# 3. Esperar ~15-30 segundos y verificar
sudo pcs status
# Resultado: g_mysql Started en nodo-b, DRBD Promoted en nodo-b
# 4. Conectar a MySQL vía IP virtual
mysql -h 192.168.1.150 -u root -p -e «SELECT * FROM laboratorio.saludos;»
# Los datos deben estar presentes
# 5. Recuperar nodo-a
sudo pcs node unstandby nodo-a
7. Consideraciones de Seguridad
| Área | Recomendación |
|---|---|
| Autenticación MySQL | Usar mysql_secure_installation tras cada instalación【9†L120-L125】. Crear cuentas con mínimos privilegios. No usar root desde aplicaciones. |
| Red y firewall | Restringir el acceso al puerto 3306 solo a IPs autorizadas【47†L75-L77】. Usar bind-address para controlar en qué interfaces escucha MySQL. |
| Comunicación del clúster | Corosync cifra el tráfico con authkey. DRBD puede usar tráfico cifrado en redes inseguras. |
| STONITH | Obligatorio en producción para evitar split‑brain y corrupción de datos. Utilizar dispositivos IPMI, iLO/DRAC o agentes de fencing adecuados【37†L17】. |
| AppArmor | Mantener activo y ajustar perfiles al cambiar rutas de archivos MySQL【25†L56】. |
| Respaldos | DRBD y replicación no sustituyen respaldos. Implementar mysqldump o herramientas como Percona XtraBackup de manera periódica. |
| Monitoreo | Supervisar estado del clúster con pcs status y crm_mon; logs en /var/log/cluster/corosync.log y /var/log/messages【37†L90-L92】. |
| Sincronización horaria | Configurar NTP o Chrony en ambos nodos para evitar inconsistencias en logs y timeouts de DRBD/Corosync【37†L23】. |
8. Problemas Comunes y Soluciones
MySQL no arranca tras mover el datadir
Causa probable: AppArmor impide el acceso al nuevo directorio. El log de errores (/var/log/mysql/error.log o la ruta configurada)【25†L53】 mostrará mensajes de permission denied.
Solución: Ajustar el perfil AppArmor como se describe en la sección 4.3 y recargar con apparmor_parser -r【25†L56】. Verificar también que los archivos en el nuevo datadir pertenezcan a mysql:mysql.
Split‑brain en DRBD
Causa: Ambos nodos se promueven a Primary simultáneamente (pérdida de comunicación sin STONITH configurado).
Solución preventiva: Habilitar STONITH y configurar correctamente la política de quórum. Si ya ocurrió, intervenir manualmente: degradar uno de los nodos a Secondary con drbdadm secondary mysqldata y reconectar con drbdadm --discard-my-data connect mysqldata en el nodo cuyos datos se descartarán.
Replica MySQL no conecta al Primary
Posibles causas y verificaciones:
| Verificación | Comando |
|---|---|
bind-address permite conexiones remotas | grep bind-address /etc/mysql/mysql.conf.d/mysqld.cnf |
| Firewall abierto en puerto 3306 | sudo ufw status |
| Usuario de replicación correcto | SELECT user, host FROM mysql.user WHERE user='replicador'; |
| Binlog habilitado | SHOW VARIABLES LIKE 'log_bin'; → debe ser ON |
server-id único en cada nodo | SHOW VARIABLES LIKE 'server_id'; |
Socket MySQL no encontrado
Causa: El archivo /var/run/mysqld/mysqld.sock no existe porque MySQL no está corriendo o el directorio no fue creado【32†L26】【32†L54-L60】.
Solución:
sudo systemctl status mysql # Verificar si está corriendo
sudo mkdir -p /var/run/mysqld
sudo chown mysql:mysql /var/run/mysqld # Asegurar permisos correctos
sudo systemctl restart mysql
Los permisos del directorio y archivo socket deben ser 755 y propiedad de mysql:mysql【32†L87-L94】.
Rendimiento subóptimo con DRBD
Trade‑off: DRBD en protocol C (síncrono) añade latencia a cada escritura porque espera confirmación del nodo peer antes de completar la operación de I/O. Para mitigar:
- Usar red dedicada de alta velocidad (10 Gbps o superior) para tráfico DRBD.
- Ajustar
innodb_buffer_pool_sizepara aprovechar la RAM disponible (típicamente 70‑80% de la RAM del servidor). - Considerar
sync_binlog = 1para máxima seguridad, asumiendo el impacto en rendimiento; valores más altos reducen la carga pero arriesgan pérdida de eventos binlog en caso de falla【18†L95】.
Archivos de logs crecen indefinidamente
Los logs de MySQL pueden ocupar espacio en disco si no se gestionan. Se recomienda configurar rotación automática y limpiar logs con la sentencia FLUSH LOGS o con mysqladmin flush-logs【25†L37-L42】. Para binlogs, la opción expire_logs_days controla la retención automática. También puede programarse una tarea con cron para eliminar logs antiguos【25†L14-L18】:
# Ejemplo: eliminar ficheros de log de más de 7 días
* * * * * find /path/to/*.log -mtime +7 -exec rm -f {} \;
Conclusión
Este laboratorio integró tres capas tecnológicas complementarias sobre Debian 13.4:
- MySQL 8.0 como RDBMS de código abierto, instalado desde el repositorio oficial de Oracle ante la ausencia de paquetes nativos MySQL en Debian【9†L47】.
- DRBD con Pacemaker/Corosync para proveer un clúster activo‑pasivo con replicación síncrona a nivel de bloque y conmutación automática del servicio. Pacemaker orquesta los recursos (DRBD, filesystem, IP virtual y MySQL) con restricciones de orden y colocación que garantizan un arranque y parada coherentes【37†L14-L17】.
- Replicación nativa de MySQL (Primary‑Replica basada en binlog) como mecanismo complementario que demuestra la sincronización a nivel de transacciones SQL, independiente del almacenamiento subyacente【47†L39】.
Trade‑off principal entre enfoques:
- DRBD/Pacemaker ofrece cero pérdida de datos y failover transparente, pero solo permite un nodo activo a la vez.
- La replicación nativa MySQL permite múltiples réplicas activas para lectura, escalando horizontalmente las consultas, pero es asíncrona por defecto y requiere gestión manual (o herramientas adicionales) para la conmutación de roles.
La combinación de ambas técnicas en un mismo entorno —aunque redundante desde el punto de vista funcional— proporciona una comprensión profunda de los mecanismos de alta disponibilidad disponibles en el ecosistema MySQL/Linux, y sienta las bases para diseñar arquitecturas adaptadas a requisitos específicos de disponibilidad, escalabilidad y presupuesto.