Glosario de Automatización • Duplicados en QoS 1

¿Por qué MQTT QoS 1 entrega mensajes duplicados?

Ingeniería Merobix • • 8 min de lectura

El nivel 1 de calidad de servicio de MQTT promete que un mensaje se entregará al menos una vez. Las palabras al menos cargan mucho peso: significan que el mismo mensaje puede llegar legítimamente dos veces. No es un bug ni un broker descompuesto - es la consecuencia directa de cómo QoS 1 garantiza la entrega sobre una red poco confiable. Esta guía explica exactamente cuándo y por qué ocurre un duplicado, qué señala la bandera DUP, por qué los consumidores de telemetría QoS 1 deben construirse para tolerar repeticiones, cuándo un duplicado importa de verdad, y por qué muchos equipos siguen prefiriendo QoS 1 sobre el handshake más pesado de QoS 2.

Volver al glosario

Duplicados en QoS 1 en una línea: MQTT QoS 1 garantiza entrega al menos una vez, lo que significa que los duplicados son posibles por diseño. Cuando un publicador envía un mensaje y el reconocimiento (PUBACK) se pierde o se demora, el publicador no puede saber si el mensaje llegó, así que lo reenvía con la bandera DUP activada. El mensaje puede por lo tanto entregarse dos veces. Por eso, los consumidores de QoS 1 deben construirse para manejar duplicados con seguridad, típicamente haciendo idempotente su procesamiento.

Cómo un reconocimiento perdido crea un duplicado

QoS 1 funciona exigiendo un reconocimiento por cada mensaje. El emisor publica un mensaje y lo conserva, esperando que el receptor devuelva un PUBACK confirmando la recepción. Solo cuando el PUBACK llega, el emisor considera entregado el mensaje y descarta su copia almacenada. Este ciclo de almacenar y reconocer es lo que convierte una red poco confiable en una garantía de al menos una vez: mientras el emisor conserve una copia y siga esperando, el mensaje no se perderá.

El duplicado surge de una falla específica: el mensaje llega, pero el reconocimiento no. Imagine que un publicador envía una lectura de telemetría, el broker la recibe y la procesa correctamente, y el broker devuelve un PUBACK - pero ese PUBACK se pierde en el camino de regreso, o la red se cae justo al enviarse. Desde el punto de vista del publicador, nada regresó. No tiene manera de distinguir un mensaje que nunca llegó de un mensaje que llegó pero cuyo reconocimiento se perdió. Ante esa ambigüedad, la única opción segura consistente con al menos una vez es reenviar, así que el publicador transmite el mensaje otra vez.

Al reenviar, el publicador activa la bandera DUP en el mensaje. DUP viene de duplicado, y es la forma del protocolo de decir esto es una retransmisión de un mensaje que ya intenté enviar, no uno nuevo. Importante: la bandera DUP es una pista sobre el intento de envío, no una llave de deduplicación confiable por sí sola - le dice al receptor que el emisor está reintentando, pero el receptor de todos modos termina con el contenido dos veces si procesó la primera copia. El resultado es que la misma lectura se entrega una segunda vez, que es exactamente lo que al menos una vez permite.

Por qué los consumidores deben ser idempotentes

Como QoS 1 puede entregar el mismo mensaje dos veces, cualquier consumidor de datos QoS 1 tiene que construirse de modo que procesar un mensaje dos veces no haga daño. La palabra técnica es idempotente: una operación es idempotente si hacerla repetidamente tiene el mismo efecto que hacerla una vez. Si un manejador simplemente almacena el último valor de un tag, es idempotente por naturaleza - escribir la misma lectura dos veces deja el mismo valor, y el duplicado es inofensivo. Los problemas aparecen cuando un manejador hace algo que acumula, como incrementar un total o anexar una fila, porque entonces la segunda copia cambia el resultado.

La forma práctica de hacer idempotente un manejador suele ser dar a los mensajes una identidad estable y hacer que el procesamiento dependa de esa identidad y no solo del hecho de que llegó un mensaje. Un consumidor puede llevar su propia noción de qué mensaje ya aplicó - por ejemplo con clave en un timestamp, un número de secuencia de la fuente o un identificador a nivel de aplicación en la carga - y saltarse o sobrescribir en lugar de reaplicar lo que ya vio. El punto clave es que la deduplicación es responsabilidad del consumidor bajo QoS 1; el protocolo entrega al menos una vez y deja a la aplicación hacer que al menos una vez se comporte como exactamente una vez donde eso importa.

No es una carga pesada para la mayoría de la telemetría, pero sí tiene que ser una decisión de diseño consciente y no una ocurrencia tardía. Un sistema que asume que cada mensaje es único y procesa cada llegada a ciegas terminará, tarde o temprano, contando doble un valor cuando un hipo real de red cause una retransmisión. Diseñar consumidores idempotentes desde el inicio significa que esos duplicados inevitables pasan inofensivos en lugar de corromper datos en silencio justo durante los momentos de problemas de red en que el comportamiento correcto más importa.

Cuándo importan los duplicados, y por qué QoS 1 sobre QoS 2

Que un duplicado importe de verdad depende por completo de lo que el valor representa. Para una medición instantánea - una presión actual, una temperatura, un nivel de tanque - un duplicado es esencialmente inofensivo, porque procesar la misma lectura dos veces solo vuelve a escribir el mismo valor actual. La segunda copia no trae información nueva y no hace daño. Este es el caso común para muchísima telemetría SCADA, y por eso al menos una vez es cómodo para la mayoría del monitoreo en tiempo real: el último valor simplemente sobrescribe, con duplicado o sin él.

El caso peligroso es cualquier cosa acumulativa. Un contador corriente, un totalizador, un volumen de flujo, un conteo de pulsos, un medidor de facturación - son valores donde procesar el mismo incremento dos veces produce un total equivocado, y el error persiste. Si el contador de volumen producido de un pozo cuenta doble un delta porque se coló un duplicado, el total queda sobreestimado y así se queda. Para valores como estos, o el consumidor deduplica con rigor, o el modelo de datos debe llevar lecturas absolutas en lugar de incrementos para que un duplicado sobrescriba en lugar de sumar. Una plataforma SCADA en la nube como Merobix que ingiere telemetría MQTT de gateways de campo está construida con esta distinción en mente, tratando distinto los valores instantáneos y los contadores acumulativos para que los duplicados de al menos una vez no corrompan totales.

Dado que los duplicados son manejables, muchos equipos eligen deliberadamente QoS 1 sobre QoS 2 aunque QoS 2 garantice entrega exactamente una vez. La razón es el costo. QoS 2 logra exactamente una vez mediante un handshake de cuatro partes por mensaje en lugar del reconocimiento único de QoS 1, lo que significa más viajes redondos, más estado sostenido en ambos extremos y más overhead - una penalización significativa en enlaces restringidos o de alta latencia como las conexiones celulares de campo. Para telemetría que es naturalmente idempotente o que un consumidor idempotente vuelve tal, QoS 1 entrega la confiabilidad que importa a una fracción del overhead, así que los equipos aceptan el duplicado ocasional como el intercambio más barato y simple en lugar de pagar QoS 2 en cada mensaje.

Preguntas frecuentes

¿Por qué MQTT QoS 1 entrega el mismo mensaje dos veces?

Porque QoS 1 garantiza entrega al menos una vez. Cuando un publicador envía un mensaje pero el reconocimiento (PUBACK) se pierde en el camino de regreso, el publicador no puede saber si el mensaje llegó, así que lo reenvía con la bandera DUP activada. Si el original de hecho había llegado, el receptor ahora lo tiene dos veces. El duplicado es el resultado esperado de garantizar la entrega sobre una red poco confiable.

¿Qué significa la bandera DUP de MQTT?

La bandera DUP marca un mensaje como retransmisión: el emisor está reintentando una publicación que ya intentó, no enviando un mensaje nuevo. Señala que la entrega es un reintento. Es una pista sobre el envío, no una llave de deduplicación por sí sola, así que un consumidor de todos modos tiene que manejar la posibilidad de que ya procesó el mismo contenido y debe deduplicar a nivel de aplicación si eso importa.

¿Por qué elegir MQTT QoS 1 en lugar de QoS 2 si QoS 2 evita duplicados?

Porque la garantía de exactamente una vez de QoS 2 cuesta un handshake de cuatro partes por mensaje, contra el reconocimiento único de QoS 1: más viajes redondos, más estado y más overhead, que sale caro en enlaces restringidos o de alta latencia como el celular. Cuando la telemetría es naturalmente idempotente o el consumidor está construido para deduplicar, QoS 1 provee la confiabilidad que importa mucho más barato, así que muchos equipos aceptan duplicados ocasionales en lugar de pagar QoS 2 en todo.

Más en Protocolos industriales
Intervalo de expiración de mensajes MQTT  •  Preámbulo HART  •  DDATA y NDATA de Sparkplug  •  NBIRTH y NDEATH  •  Niveles de QoS de MQTT (0, 1, 2)  •  Todo en Protocolos industriales →
Capacitación SCADA gratuita para operadores
Merobix University - 70 lecciones en video y 261 preguntas de examen, del primer inicio de sesión a los reportes de cumplimiento (contenido en inglés). Sin llamada de ventas.
Comenzar gratis →