Fundamentos

Níveis de QoS do MQTT explicados: QoS 0, 1 e 2

QoS do MQTT explicado: como QoS 0, 1 e 2 funcionam pacote a pacote, o que é a regra de rebaixamento, como as sessões afetam a entrega e qual nível escolher.

Atualizado · 7 min de leitura

O QoS do MQTT (Quality of Service, qualidade de serviço) define o quanto o protocolo se esforça para entregar uma mensagem. Existem três níveis de QoS — 0, 1 e 2 — e cada um adiciona pacotes de confirmação em troca de uma garantia mais forte. Escolher o nível certo é uma das decisões de design mais importantes em um sistema MQTT: baixo demais e você perde dados; alto demais e você desperdiça banda e latência.

Os níveis de QoS em resumo

QoSGarantiaPacotes por saltoPode haver duplicatas?
0No máximo uma vez1 (PUBLISH)Não — mas mensagens podem se perder
1Pelo menos uma vez2 (PUBLISH, PUBACK)Sim
2Exatamente uma vez4 (PUBLISH, PUBREC, PUBREL, PUBCOMP)Não

Um detalhe importante: o QoS é negociado por salto. O QoS do publicador rege o trajeto até o broker, e o QoS da assinatura rege o trajeto do broker até cada assinante.

QoS 0 — no máximo uma vez

O remetente transmite o PUBLISH uma vez e esquece. Não há confirmação nem packet identifier. Se a conexão TCP cair enquanto a mensagem está em trânsito, ela se perde.

Fluxo do QoS 0
Sender                     Receiver
  | ---- PUBLISH (QoS 0) ---> |
  |                           |  (no reply)

O QoS 0 é a opção mais barata e funciona perfeitamente para telemetria de alta frequência — uma leitura de temperatura por segundo, uma posição GPS, um heartbeat — em que a próxima mensagem substitui a que se perdeu. Observe que o TCP continua protegendo contra corrupção e reordenação em uma conexão ativa; o risco é perder mensagens quando as conexões caem.

QoS 1 — pelo menos uma vez

O remetente atribui um packet identifier, armazena a mensagem e aguarda um PUBACK com o mesmo identificador. Até a confirmação chegar, a mensagem é considerada em trânsito (in flight). Se a conexão cair antes, o remetente a retransmite com a flag DUP ativada quando a sessão for retomada.

Fluxo do QoS 1
Sender                          Receiver
  | ---- PUBLISH (QoS 1, id=7) ---> |  store + deliver
  | <--------- PUBACK (id=7) ------ |
  |  delete stored message          |

O problema: se o PUBACK se perder, o receptor já processou a mensagem e a recebe de novo na retransmissão. Por isso, o QoS 1 garante a entrega, mas permite duplicatas. Para a maioria das aplicações, esse é o equilíbrio certo — torne seus handlers idempotentes (por exemplo, incluindo um ID de mensagem ou timestamp no payload) e você terá confiabilidade com pouco overhead.

QoS 2 — exatamente uma vez

O QoS 2 usa um handshake de quatro etapas para que nenhum dos lados entregue a mensagem duas vezes:

Fluxo do QoS 2
Sender                          Receiver
  | ---- PUBLISH (QoS 2, id=9) ---> |  store id=9, (deliver)
  | <--------- PUBREC (id=9) ------ |
  | ---------- PUBREL (id=9) -----> |  release id=9
  | <--------- PUBCOMP (id=9) ----- |
  |  done                           |
  1. PUBLISH — o remetente transmite a mensagem e guarda uma cópia.
  2. PUBREC — o receptor confirma o recebimento e registra o packet identifier. Qualquer PUBLISH retransmitido com esse identificador é reconhecido como duplicata e não é entregue de novo.
  3. PUBREL — o remetente descarta a mensagem e avisa o receptor que ele pode liberar o identificador.
  4. PUBCOMP — o receptor confirma; o identificador pode ser reutilizado.

O custo são duas idas e voltas por salto e estado mantido nos dois lados. O QoS 2 faz sentido para mensagens em que uma duplicata é realmente prejudicial e não pode ser filtrada na aplicação — eventos de faturamento ou comandos únicos para atuadores, por exemplo. Na prática, muitas equipes usam QoS 1 com deduplicação.

A regra de rebaixamento: QoS efetivo

Um assinante solicita um QoS máximo no seu pacote SUBSCRIBE, e o broker devolve o QoS concedido no SUBACK. Cada mensagem é então entregue com o menor entre o QoS de publicação e o QoS concedido na assinatura:

Publicada comAssinada comEntregue com
QoS 2QoS 0QoS 0
QoS 1QoS 2QoS 1
QoS 0QoS 1QoS 0
QoS 2QoS 2QoS 2

Os brokers também podem limitar o QoS: no MQTT 5, um broker pode anunciar Maximum QoS no CONNACK, e alguns brokers ou serviços de nuvem não suportam QoS 2. Sempre confira o QoS concedido no SUBACK em vez de supor que recebeu o que pediu.

QoS e sessões: o que acontece offline

O QoS só protege mensagens enquanto existe uma sessão. Com uma clean session (cleanSession=true no 3.1.1, cleanStart=true com session expiry 0 no MQTT 5), o broker descarta as assinaturas e as mensagens pendentes assim que o cliente se desconecta — então mensagens QoS 1 e 2 publicadas enquanto você está offline simplesmente nunca chegam até você.

Para receber mensagens que chegam enquanto um cliente está offline, você precisa de três coisas:

  • um client ID estável e único,
  • uma sessão persistente (cleanSession=false ou, no MQTT 5, um Session Expiry Interval diferente de zero),
  • uma assinatura com QoS 1 ou 2, e mensagens publicadas com QoS 1 ou 2.

Observe também que a retransmissão de mensagens não confirmadas acontece quando a sessão é retomada após uma reconexão — nem o 3.1.1 nem o 5.0 exigem reenvio em uma conexão ativa, porque o TCP já cuida das perdas nesse caso.

Testando o QoS na prática

Você pode ver o QoS em ação com a CLI do Mosquitto. A flag -d imprime todos os pacotes, então dá para ver PUBREC/PUBREL/PUBCOMP passando:

bash
# subscriber with a persistent session (-c) and fixed client ID
mosquitto_sub -h broker.emqx.io -t 'testmqtt/qos-demo/#' -q 2 -c -i qos-demo-sub -d

# publish at QoS 2
mosquitto_pub -h broker.emqx.io -t 'testmqtt/qos-demo/order' -m 'order-1001' -q 2 -d

Pare o assinante, publique algumas mensagens QoS 1 e inicie-o de novo com o mesmo client ID: as mensagens enfileiradas devem chegar. No navegador, o cliente MQTT online permite escolher o QoS por assinatura e por publicação. Para mais cenários de teste, veja como testar um broker MQTT.

Teste no cliente MQTT online

Como escolher um nível de QoS

  • QoS 0 — dados frequentes de sensores, posições e métricas em que só o valor mais recente importa.
  • QoS 1 — o padrão sensato para eventos, alertas e comandos; combine-o com handlers idempotentes.
  • QoS 2 — casos raros em que duplicatas são caras e não podem ser deduplicadas depois.

O QoS trabalha em conjunto com as mensagens retidas (retained) e o Last Will; se você é novo no protocolo, comece por o que é MQTT.

Perguntas frequentes

Qual nível de QoS do MQTT devo usar?

Use QoS 0 para telemetria frequente em que uma amostra perdida não faz diferença, QoS 1 para a maioria dos eventos e comandos (com handlers idempotentes) e QoS 2 apenas quando duplicatas são realmente prejudiciais e você não consegue deduplicá-las na aplicação.

Por que recebi uma mensagem QoS 1 duas vezes?

QoS 1 é entrega pelo menos uma vez. Se a confirmação se perder, normalmente porque a conexão caiu, o remetente retransmite a mensagem com a flag DUP ativada após reconectar, e o receptor pode vê-la duas vezes.

O QoS 2 garante entrega exatamente uma vez de ponta a ponta?

Não. O QoS se aplica a cada salto separadamente: do publicador ao broker e do broker ao assinante. O assinante recebe o menor entre o QoS de publicação e o QoS da sua assinatura, e mensagens para clientes offline só são guardadas se eles tiverem uma sessão persistente.