Un clúster de RabbitMQ agrupa varios nodos que comparten usuarios, virtual hosts, exchanges y colas, de modo que los clientes pueden conectarse a cualquiera de ellos. Para que los mensajes no se pierdan cuando cae un nodo hay que usar colas quorum, que replican su contenido con el algoritmo Raft en varios nodos. En este tutorial instalarás RabbitMQ 4 desde el repositorio oficial en tres servidores Ubuntu 24.04, formarás el clúster con descubrimiento de pares por archivo de configuración y comprobarás que una cola quorum sigue funcionando tras apagar un nodo.

Requisitos previos

Para seguir esta guía necesitas:

  • Tres servidores con Ubuntu 24.04 LTS (x86_64), por ejemplo tres VPS de CubePath, con al menos 2 GB de RAM cada uno.
  • Una red privada entre ellos. En los ejemplos se usan 10.0.0.11, 10.0.0.12 y 10.0.0.13; sustitúyelas por tus IP privadas.
  • Un usuario no root con privilegios sudo en cada servidor.
  • UFW activo con el acceso SSH permitido.

Tres nodos es el mínimo razonable: Raft necesita mayoría, así que un clúster de 3 tolera la caída de 1 y uno de 5 tolera la de 2. Un clúster de 2 nodos no tolera ninguna caída.

Salvo que se indique lo contrario, ejecuta cada paso en los tres servidores.

Paso 1: Configurar nombres de host y resolución

RabbitMQ identifica cada nodo como rabbit@<nombre corto del host>, y los nodos deben poder resolver los nombres de los demás. Asigna un nombre a cada servidor, rabbit1, rabbit2 y rabbit3 respectivamente. En el primero:

sudo hostnamectl set-hostname rabbit1

Repite en los otros dos con rabbit2 y rabbit3. Después, en los tres, añade las entradas a /etc/hosts:

sudo nano /etc/hosts
10.0.0.11 rabbit1
10.0.0.12 rabbit2
10.0.0.13 rabbit3

Comprueba que cada nodo alcanza a los demás por nombre:

ping -c 2 rabbit2
PING rabbit2 (10.0.0.12) 56(84) bytes of data.
64 bytes from rabbit2 (10.0.0.12): icmp_seq=1 ttl=64 time=0.412 ms

Paso 2: Abrir los puertos del clúster en la red privada

Los nodos se comunican por estos puertos:

PuertoUso
4369/tcpepmd, descubrimiento de nodos Erlang
25672/tcpComunicación entre nodos
35672-35682/tcpHerramientas CLI entre nodos
5672/tcpClientes AMQP
15672/tcpInterfaz web de administración

Permítelos solo desde la red privada, ajustando 10.0.0.0/24 a tu rango:

sudo ufw allow from 10.0.0.0/24 to any port 4369,25672,5672,15672 proto tcp
sudo ufw allow from 10.0.0.0/24 to any port 35672:35682 proto tcp

No abras ninguno de estos puertos a Internet. Si tus aplicaciones están fuera de la red privada, publícalas a través de una VPN o de un balanceador con TLS.

Paso 3: Instalar Erlang y RabbitMQ desde el repositorio oficial

La versión de RabbitMQ que trae Ubuntu 24.04 es antigua y no recibe soporte. El equipo de RabbitMQ mantiene repositorios con versiones actuales de Erlang y RabbitMQ. Instala las herramientas necesarias e importa su clave de firma:

sudo apt update
sudo apt install curl gnupg
sudo install -m 0755 -d /etc/apt/keyrings
curl -1sLf "https://keys.openpgp.org/vks/v1/by-fingerprint/0A9AF2115F4687BD29803A206B73A36E6026DFCA" \
  | sudo gpg --dearmor -o /etc/apt/keyrings/rabbitmq.gpg

Añade los repositorios de Erlang y de RabbitMQ:

sudo nano /etc/apt/sources.list.d/rabbitmq.list
deb [arch=amd64 signed-by=/etc/apt/keyrings/rabbitmq.gpg] https://deb1.rabbitmq.com/rabbitmq-erlang/ubuntu/noble noble main
deb [arch=amd64 signed-by=/etc/apt/keyrings/rabbitmq.gpg] https://deb2.rabbitmq.com/rabbitmq-erlang/ubuntu/noble noble main
deb [arch=amd64 signed-by=/etc/apt/keyrings/rabbitmq.gpg] https://deb1.rabbitmq.com/rabbitmq-server/ubuntu/noble noble main
deb [arch=amd64 signed-by=/etc/apt/keyrings/rabbitmq.gpg] https://deb2.rabbitmq.com/rabbitmq-server/ubuntu/noble noble main

Instala Erlang y RabbitMQ:

sudo apt update
sudo apt install erlang-base \
  erlang-asn1 erlang-crypto erlang-eldap erlang-ftp erlang-inets \
  erlang-mnesia erlang-os-mon erlang-parsetools erlang-public-key \
  erlang-runtime-tools erlang-snmp erlang-ssl \
  erlang-syntax-tools erlang-tftp erlang-tools erlang-xmerl
sudo apt install rabbitmq-server

Comprueba la versión instalada:

sudo rabbitmq-diagnostics server_version
Asking node rabbit@rabbit1 for its RabbitMQ version...
4.3.6

El número exacto dependerá de la última versión publicada. Es importante que los tres nodos tengan la misma versión.

Los nodos de un clúster se autentican entre sí con un secreto compartido, la cookie de Erlang, guardada en /var/lib/rabbitmq/.erlang.cookie. El paquete genera una distinta en cada servidor, así que hay que copiar la de rabbit1 a los otros dos.

En rabbit1, muestra la cookie:

sudo cat /var/lib/rabbitmq/.erlang.cookie
QXNZVRPLKCWBHJFDMTEA

En rabbit2 y rabbit3, detén RabbitMQ y sustituye la cookie por ese valor exacto (el tuyo será distinto):

sudo systemctl stop rabbitmq-server
echo -n 'QXNZVRPLKCWBHJFDMTEA' | sudo tee /var/lib/rabbitmq/.erlang.cookie > /dev/null
sudo chown rabbitmq:rabbitmq /var/lib/rabbitmq/.erlang.cookie
sudo chmod 400 /var/lib/rabbitmq/.erlang.cookie

Trata la cookie como una contraseña: quien la tenga y alcance el puerto 25672 controla el clúster.

Paso 5: Configurar el descubrimiento de pares

En lugar de unir los nodos a mano uno a uno, RabbitMQ puede formar el clúster solo al arrancar si cada nodo conoce la lista de miembros. Este mecanismo, classic_config, es el recomendado cuando los nodos se conocen de antemano. En los tres servidores, crea el archivo de configuración:

sudo nano /etc/rabbitmq/rabbitmq.conf
cluster_formation.peer_discovery_backend = classic_config
cluster_formation.classic_config.nodes.1 = rabbit@rabbit1
cluster_formation.classic_config.nodes.2 = rabbit@rabbit2
cluster_formation.classic_config.nodes.3 = rabbit@rabbit3

# Reparte los líderes de las colas entre los nodos
queue_leader_locator = balanced

El descubrimiento de pares solo actúa en nodos vacíos, es decir, en su primer arranque. Como el paquete ya arrancó RabbitMQ una vez al instalarse, borra los datos que creó para que cada nodo arranque en blanco. En este punto no contienen nada útil:

sudo systemctl stop rabbitmq-server
sudo rm -rf /var/lib/rabbitmq/mnesia

Paso 6: Arrancar el clúster

Arranca RabbitMQ en los tres nodos, empezando por rabbit1:

sudo systemctl start rabbitmq-server

Cuando los tres estén en marcha, comprueba el estado del clúster desde cualquiera de ellos:

sudo rabbitmqctl cluster_status
Cluster status of node rabbit@rabbit1 ...
Basics

Cluster name: rabbit@rabbit1
...
Running Nodes

rabbit@rabbit1
rabbit@rabbit2
rabbit@rabbit3

Los tres nodos deben aparecer en Running Nodes. Si alguno arrancó como clúster independiente, consulta la sección de solución de problemas.

Paso 7: Crear un usuario administrador y un virtual host

Los usuarios, permisos y virtual hosts se replican en todo el clúster, así que estos comandos se ejecutan solo en rabbit1. El usuario guest únicamente puede conectarse desde localhost, por lo que necesitas uno propio. Sustituye your_strong_password por una contraseña robusta:

sudo rabbitmqctl add_user admin 'your_strong_password'
sudo rabbitmqctl set_user_tags admin administrator

Crea un virtual host para tu aplicación en el que las colas sean quorum por defecto. Así, cualquier cola que declare un cliente sin indicar tipo será replicada:

sudo rabbitmqctl add_vhost app --default-queue-type quorum
sudo rabbitmqctl set_permissions -p app admin ".*" ".*" ".*"

Elimina el usuario guest, que no necesitas:

sudo rabbitmqctl delete_user guest

Activa la interfaz web de administración en los tres nodos (este comando sí es por nodo):

sudo rabbitmq-plugins enable rabbitmq_management

Desde un equipo de la red privada, abre http://10.0.0.11:15672 e inicia sesión con admin. En la pestaña Overview verás los tres nodos.

Paso 8: Crear y probar una cola quorum

Para probar el clúster usarás un pequeño script en Python con la librería pika. En rabbit1, prepara un entorno virtual:

sudo apt install python3-venv
python3 -m venv ~/rmq-venv
~/rmq-venv/bin/pip install pika

Crea un script que publique 1.000 mensajes persistentes en la cola pedidos. Los clientes pueden recibir varios hosts y probarán el siguiente si uno no responde:

nano ~/publicar.py
import pika

credenciales = pika.PlainCredentials("admin", "your_strong_password")
nodos = [
    pika.ConnectionParameters(host=h, virtual_host="app", credentials=credenciales)
    for h in ("rabbit1", "rabbit2", "rabbit3")
]

conexion = pika.BlockingConnection(nodos)
canal = conexion.channel()
canal.confirm_delivery()

# El vhost "app" crea colas quorum por defecto
canal.queue_declare(queue="pedidos", durable=True)

for i in range(1000):
    canal.basic_publish(
        exchange="",
        routing_key="pedidos",
        body=f"pedido {i}".encode(),
        properties=pika.BasicProperties(delivery_mode=pika.DeliveryMode.Persistent),
    )

print("1000 mensajes confirmados")
conexion.close()

Ejecútalo:

~/rmq-venv/bin/python ~/publicar.py
1000 mensajes confirmados

Comprueba el tipo de la cola, su líder y sus réplicas:

sudo rabbitmqctl list_queues -p app name type leader members messages
name     type    leader          members                                            messages
pedidos  quorum  rabbit@rabbit2  [rabbit@rabbit2, rabbit@rabbit1, rabbit@rabbit3]  1000

La cola tiene una réplica en cada nodo y uno de ellos actúa como líder.

Paso 9: Simular la caída de un nodo

Apaga RabbitMQ en el nodo que aparece como líder, en este ejemplo rabbit2:

sudo systemctl stop rabbitmq-server

Desde rabbit1, consulta de nuevo la cola:

sudo rabbitmqctl list_queues -p app name leader messages
name     leader          messages
pedidos  rabbit@rabbit1  1000

Las réplicas restantes han elegido un nuevo líder en pocos segundos y los 1.000 mensajes siguen disponibles. Puedes volver a ejecutar publicar.py para comprobar que se sigue aceptando escritura con un nodo caído.

Vuelve a arrancar el nodo:

sudo systemctl start rabbitmq-server

Al reincorporarse, rabbit2 se sincroniza con el líder automáticamente. Comprueba el estado detallado de las réplicas:

sudo rabbitmq-queues quorum_status pedidos --vhost app

Los tres miembros deben aparecer con el mismo Commit Index.

Solución de problemas

  • Un nodo forma su propio clúster en vez de unirse: tenía datos previos cuando arrancó. Detén el servicio en ese nodo, borra /var/lib/rabbitmq/mnesia (solo si es un nodo nuevo sin datos) y vuelve a arrancarlo. Como alternativa, en RabbitMQ 4.1 y posteriores puedes ejecutar en él sudo rabbitmqctl join_cluster rabbit@rabbit1, que descarta sus datos locales y lo une al clúster.
  • Authentication failed (rejected by the remote node), please check the Erlang cookie: las cookies no coinciden. Compara sudo md5sum /var/lib/rabbitmq/.erlang.cookie en los tres nodos.
  • unable to connect to epmd o nodos inalcanzables: revisa /etc/hosts y las reglas de UFW del paso 2. Prueba la conectividad con nc -zv rabbit2 25672.
  • Retirar un nodo definitivamente: detén RabbitMQ en él y, desde otro nodo, ejecuta sudo rabbitmqctl forget_cluster_node rabbit@rabbit3.
  • Revisar los registros: sudo journalctl -u rabbitmq-server -n 100 --no-pager o los archivos de /var/log/rabbitmq/.

Conclusión

Tienes un clúster de RabbitMQ 4 de tres nodos en Ubuntu 24.04, formado automáticamente a partir de la configuración, con un virtual host que crea colas quorum replicadas y una prueba real de conmutación por error. Como siguientes pasos, puedes activar TLS en los listeners AMQP y de administración, exportar métricas con el plugin rabbitmq_prometheus y hacer copias de la definición del clúster con rabbitmqctl export_definitions.