Caddy HA failover¶
Procedimiento para validar manualmente que el VIP 192.168.0.XXX migra de
caddy-primary (LXC 270, pmx-50) a caddy-secondary (LXC 271, pmx-51) cuando
el primario cae. Diseño documentado en
ADR-0007 §F4.
Cuándo correr este drill
- Tras un cambio en
keepalived.confomanaged.caddy. - Mensualmente como prueba de salud (cron sugerido día 1 de mes).
- Antes de un reboot planificado del nodo primario.
Pre-flight¶
```bash
Verificar que el VIP está donde toca (primary)¶
ssh pmx-50 'pct exec 270 -- ip -4 addr show eth0 | grep 192.168.0.XXX'
debe aparecer la IP secundaria .250 además de la .247¶
```
```bash
Confirmar que ambos Caddy responden por su IP propia¶
curl --resolve grafana.monxas.casa:443:192.168.0.XXX -fsSk https://grafana.monxas.casa/ -o /dev/null && echo OK-primary curl --resolve grafana.monxas.casa:443:192.168.0.XXX -fsSk https://grafana.monxas.casa/ -o /dev/null && echo OK-secondary ```
Si alguno falla, no continuar con el drill — investigar antes.
Disparar failover¶
Parar Caddy en el primario. keepalived lleva track_process caddy con
weight -20, así que al parar el proceso la prioridad cae y el VIP migra.
bash
ssh pmx-50 'pct exec 270 -- systemctl stop caddy'
Esperar 3-5 segundos (VRRP advertise interval por defecto = 1s; migración suele ser <2s).
Verificación¶
```bash
El VIP debe estar ahora en el secundario¶
ssh pmx-51 'pct exec 271 -- ip -4 addr show eth0 | grep 192.168.0.XXX' && echo "VIP migrado OK"
Tráfico real funcionando via VIP¶
curl --resolve grafana.monxas.casa:443:192.168.0.XXX -fsSk https://grafana.monxas.casa/ -o /dev/null && echo "Caddy via VIP OK" ```
Bonus — verificar desde fuera (CF Tunnel apunta al VIP):
bash
curl -fsS https://grafana.monxas.casa/ -o /dev/null && echo "External OK"
Rollback (volver al primary)¶
Levantar Caddy en LXC 270. Al recuperar el proceso, prioridad sube y VIP regresa:
bash
ssh pmx-50 'pct exec 270 -- systemctl start caddy'
sleep 5
ssh pmx-50 'pct exec 270 -- ip -4 addr show eth0 | grep 192.168.0.XXX' && echo "VIP back to primary"
Troubleshooting¶
| Síntoma | Causa probable | Fix |
|---|---|---|
| VIP no migra al parar caddy | track_process mal escrito en keepalived.conf o falta weight -20 |
Revisar /etc/keepalived/keepalived.conf ambos nodos |
| VIP migra pero Caddy secondary 502 | managed.caddy desactualizado en LXC 271 |
Re-sync: python3 ~/scripts/homelab-ctl.py sync --yes |
| VIP queda en split-brain (ambos lo anuncian) | VRRP packets bloqueados por firewall entre nodos | Comprobar conectividad multicast/unicast VRRP entre .247 y .248 |
| Failover OK pero CF Tunnel sigue 502 | cloudflared cachea conexión al primario |
ssh pmx-51 'pct exec 123 -- systemctl restart cloudflared' |
| Sablier-protected services tarda 30s+ tras failover | State Sablier no compartido (esperado, ver ADR §F4) | Aceptable; re-wake una vez |
Notas¶
- No apagar el LXC 270 entero para el drill; basta con parar
caddy.service. Apagar el LXC también dispara la migración pero complica el rollback. - Frecuencia esperada de failover real: <1/mes. Si pasa más, hay un problema upstream (kernel panic, OOM, red).