ntfy v2.32.0 ordena los trabajos de un clúster pasivo
La nueva versión evita que los nodos pasivos compitan por tareas de mantenimiento en una base de datos compartida.
El problema no es publicar mensajes
Montar varias instancias de ntfy detrás de un proxy inverso parece sencillo cuando todas comparten PostgreSQL. El detalle aparece en las tareas que no responden a una petición concreta: limpieza de mensajes caducados, adjuntos, tokens o actualización de métricas. Si cada nodo ejecuta esos trabajos por su cuenta, la base de datos recibe trabajo duplicado y una réplica puede sobrescribir el estado calculado por otra.
ntfy server v2.32.0 corrige una parte importante de ese escenario experimental. Las tareas de mantenimiento que escriben en la base compartida pasan a ejecutarse solo en el líder del clúster. Esto permite tener un nodo pasivo sin que interfiera con el recuento total de mensajes publicados ni con los procesos de limpieza.
La versión se publicó el 18 de octubre de 2026. También registra en cada almacén de base de datos la versión mínima de esquema compatible, de modo que una versión antigua de ntfy puede negarse a arrancar si una actualización posterior aplicó una migración incompatible. Es una medida prudente para evitar que una instancia antigua interprete mal datos migrados.
Dónde encaja en un homelab
Para mí, ntfy tiene sentido como pieza de notificación transversal. Un cron puede avisar al terminar una copia de seguridad, Docker Compose puede informar de un fallo de arranque y una aplicación Laravel puede publicar una alerta mediante una petición HTTP. No hace falta convertirlo en el centro de la observabilidad para que resulte útil: basta con que los avisos importantes lleguen al teléfono o al escritorio.
En una instalación pequeña, una única instancia suele ser suficiente. Pero si ya tengo PostgreSQL, un proxy inverso y varias máquinas, poder repartir conexiones de clientes entre varios nodos resulta atractivo. El nodo pasivo sirve para casos concretos, como clientes de prueba o una instancia que no debe entrar en el reparto habitual del balanceador.
La documentación define un nodo passive como uno que no puede liderar los trabajos singleton del clúster y que tampoco queda listo para recibir tráfico del balanceador. Por eso no es una réplica de alta disponibilidad que pueda sustituir sin más a un nodo activo. Es una función con un propósito limitado, y conviene diseñar la topología alrededor de esa limitación.
Una configuración mínima del clúster
El clúster de ntfy sigue marcado como experimental y requiere PostgreSQL mediante database-url. Cada nodo necesita un identificador estable, una dirección privada para el tráfico entre nodos y un secreto compartido. La dirección de escucha del clúster no debe quedar expuesta a Internet.
Este ejemplo usa la configuración documentada para un nodo activo. En los demás nodos hay que cambiar el identificador, la IP de escucha y la URL anunciada; el secreto debe ser idéntico en todos. Para un nodo que no vaya detrás del balanceador, el rol puede ser passive.
base-url: "https://ntfy.example.com"
database-url: "postgres://ntfy:password@postgres:5432/ntfy"
experimental-cluster-node-id: "ntfy-1"
experimental-cluster-listen: "10.0.0.5:2587"
experimental-cluster-advertise-url: "http://10.0.0.5:2587"
experimental-cluster-secret: "un-secreto-largo-y-compartido"
experimental-cluster-role: "active"El balanceador debe comprobar /v1/ready, no /v1/health. La diferencia importa porque un nodo pasivo nunca se considera listo para entrar en el reparto de tráfico. El endpoint de salud solo informa de la conexión del propio nodo con la base de datos, no de que todos los enlaces entre nodos funcionen correctamente.
Alertas sencillas desde scripts y aplicaciones
La parte práctica de ntfy sigue siendo su API HTTP. Un script de cron o un contenedor puede enviar un POST al tema correspondiente con curl, sin SDK específico ni una cola adicional. Laravel puede hacer lo mismo desde una notificación propia, un listener de eventos o un comando programado usando su cliente HTTP.
Un ejemplo básico para informar de un backup completado sería este. El encabezado Title es opcional, pero ayuda a distinguir alertas cuando varios servicios publican en el mismo tema. En un servidor propio sustituiría el dominio y protegería el tema con la configuración de acceso de ntfy.
curl --fail \
-H "Title: Copia de seguridad" \
-d "El backup nocturno ha terminado correctamente." \
https://ntfy.example.com/infra-alertasSeparar temas por función evita que las notificaciones pierdan contexto. Yo usaría nombres distintos para infraestructura, copias, errores de aplicación y tareas domésticas, en lugar de enviar todo a un único canal. También evita que una alerta de bajo interés acabe ocultando un fallo que requiere intervención.
La letra pequeña
Este cambio no convierte el clúster experimental en una configuración lista para producción. La propia documentación indica que las opciones experimental-cluster-* todavía no están preparadas para ese uso. Si ntfy es el único canal de alertas de un servicio crítico, no asumiría que varias instancias eliminan todos los riesgos operativos.
Los límites de uso se aplican por nodo. En un clúster, un cliente que distribuya peticiones entre varios nodos puede consumir los límites de cada uno por separado. Además, los mensajes publicados con cache: no no llegan a otros nodos con la misma garantía, porque no quedan almacenados en la base de datos compartida.
También hay que revisar la red privada entre nodos. Si el tráfico del puerto de clúster funciona en una dirección pero falla en la otra, las alertas pueden llegar tarde mediante la lectura de la base de datos aunque los nodos sigan mostrando un estado saludable. El comando ntfy cluster status sirve para comprobar la visión que cada nodo tiene de sus pares y detectar ese tipo de problema.
La mejora de v2.32.0 merece la pena si ya estaba probando el clúster con PostgreSQL y necesitaba un nodo pasivo que no compitiera por el mantenimiento. Para una instalación doméstica normal, actualizar no obliga a rediseñar nada. La ganancia está en que el comportamiento del clúster queda un poco menos expuesto a carreras entre réplicas.
Fuente: lanzamiento de ntfy v2.32.0 Documentación oficial de ntfy