Está en la página 1de 34

Protocolo MQTT: concepto y

aplicaciones
Aproveche el máximo potencial de sus dispositivos IoT con el protocolo
MQTT.

GUÍA DE CONCEPTO
Este proyecto le introducirá a los elementos esenciales de MQTT, uno de los
protocolos más populares para aplicaciones IoT.

Siguiendo los pasos de esta guía, usted comprenderá el funcionamiento del


protocolo MQTT utilizando correctamente brokers y clientes MQTT. Será
capaz de conectarse a la plataforma ThingWorx, pudiendo actualizar
Propiedades, y realizar una serie de acciones para sus aplicaciones IoT. Este
protocolo es ideal para aplicaciones IoT por su simpleza, flexibilidad y
ligereza en instalación, manejo y mantención.
Conceptos MQTT
Definición
MQTT es un protocolo de transporte de mensajería de publicación/suscripción
cliente-servidor. Es ligero, abierto, sencillo y está diseñado para ser fácil de
implementar. Estas características lo hacen ideal para su uso en muchas
situaciones, incluso en entornos limitados, como la comunicación en
contextos de Máquina a Máquina (M2M) e Internet de las Cosas (IoT), donde
se requiere una pequeña huella de código y/o el ancho de banda de la red es
muy importante.

Es un protocolo muy ligero y binario, y debido a su mínima sobrecarga de


paquetes, MQTT sobresale en la transferencia de datos por cable en
comparación con protocolos como HTTP. Otro aspecto importante del
protocolo es que MQTT es extremadamente fácil de implementar en el lado
del cliente. La facilidad de uso fue una de las principales preocupaciones en
el desarrollo de MQTT y hace que sea un ajuste perfecto para los dispositivos
con recursos limitados hoy en día.

Un poco de historia
El protocolo MQTT fue inventado en 1999 por Andy Stanford-Clark (IBM) y
Arlen Nipper (Arcom, ahora Cirrus Link). Necesitaban un protocolo que
permitiera una pérdida mínima de batería y un ancho de banda mínimo para
conectar con oleoductos vía satélite. Los dos inventores especificaron varios
requisitos para el futuro protocolo:
● Implementación sencilla
● Entrega de datos con calidad de servicio (QoS)
● Ligereza y eficiencia del ancho de banda
● Agnóstico de datos*
● Conocimiento continuo de la sesión
Estos objetivos siguen siendo el núcleo de MQTT. Sin embargo, el enfoque
principal del protocolo ha cambiado de los sistemas integrados propietarios a
los casos de uso abiertos del Internet de las cosas (IoT). Este cambio de
enfoque ha creado mucha confusión sobre el significado de las siglas MQTT.
La respuesta corta es que MQTT ya no se considera un acrónimo. MQTT es
simplemente el nombre del protocolo. "MQ" se refiere a MQ Series, un
producto que IBM desarrolló para soportar el transporte de telemetría MQ.
Cuando Andy y Arlen crearon su protocolo en 1999, le pusieron el nombre del
producto de IBM.

*En informática, se dice que un dispositivo o programa de software es


agnóstico o agnóstico de datos si el método o formato de transmisión de
datos es irrelevante para la función del dispositivo o programa. Esto significa
que el dispositivo o programa puede recibir datos en múltiples formatos o de
múltiples fuentes, y seguir procesando esos datos de forma eficaz.

Modelo Publicador/suscriptor
El modelo MQTT publish/subscribe (también conocido como pub/sub) ofrece
una alternativa a la arquitectura tradicional cliente-servidor. En el modelo
cliente-servidor, un cliente se comunica directamente con un endpoint.El
modelo pub/sub desacopla el cliente que envía un mensaje (el publicador)
del cliente o clientes que reciben los mensajes (los suscriptores). Los
publicadores y los suscriptores nunca se ponen en contacto directamente. De
hecho, ni siquiera saben que el otro existe. La conexión entre ellos es
gestionada por un tercer componente (el broker). El trabajo del broker es
filtrar todos los mensajes entrantes y distribuirlos correctamente a los
suscriptores. Así que vamos a profundizar un poco más en algunos de los
aspectos generales de pub/sub (hablaremos de los detalles de MQTT en un
minuto).
El aspecto más importante de pub/sub es la disociación entre el publicador
del mensaje y el receptor (suscriptor). Este desacoplamiento tiene varias
dimensiones:

● Desacoplamiento espacial: El editor y el suscriptor no necesitan


conocerse (por ejemplo, no hay intercambio de dirección IP y puerto).
● Desacoplamiento temporal: El editor y el suscriptor no necesitan
funcionar al mismo tiempo.
● Desacoplamiento de la sincronización: No es necesario interrumpir las
operaciones de ambos componentes durante la publicación o la
recepción.
En resumen, el modelo MQTT pub/sub elimina la comunicación directa entre
el publicador del mensaje y el receptor/suscriptor. La actividad de filtrado del
broker permite controlar qué cliente/suscriptor recibe qué mensaje. El
desacoplamiento tiene tres dimensiones: espacio, tiempo y sincronización.

MQTT - ¿Qué es y cuáles son sus principales características?


Ahora que hemos explorado el modelo de publicación/suscripción en
general, vamos a centrarnos en MQTT específicamente. Dependiendo de lo
que quieras conseguir, MQTT incorpora todos los aspectos de pub/sub que
hemos mencionado:

● MQTT desvincula espacialmente al publicador y al suscriptor. Para


publicar o recibir mensajes, los publicadores y suscriptores sólo
necesitan conocer el nombre de host/IP y el puerto del broker.
● MQTT desacopla por tiempo. Aunque la mayoría de los casos de uso de
MQTT entregan los mensajes en tiempo casi real, si se desea, el broker
puede almacenar los mensajes para los clientes que no están en línea.
(Se deben cumplir dos condiciones para almacenar los mensajes: que
el cliente se haya conectado con una sesión persistente y se haya
suscrito a un tópico con una calidad de servicio superior a 0).
● MQTT funciona de forma asíncrona. Como la mayoría de las bibliotecas
de clientes funcionan de forma asíncrona y se basan en callbacks o un
modelo similar, las tareas no se bloquean mientras se espera un
mensaje o se publica un mensaje. En ciertos casos de uso, la
sincronización es deseable y posible. Para esperar un determinado
mensaje, algunas bibliotecas tienen APIs síncronas. Pero el flujo suele
ser asíncrono.

Otra cosa que hay que mencionar es que MQTT es especialmente fácil de
usar en el lado del cliente. La mayoría de los sistemas pub/sub tienen la
lógica en el lado del broker, pero MQTT es realmente la esencia de pub/sub
cuando se utiliza una librería cliente y eso lo convierte en un protocolo ligero
para dispositivos pequeños y limitados.

Filtrado de mensajes
Está claro que el broker MQTT juega un papel fundamental en el proceso
pub/sub. Pero, ¿cómo consigue el broker filtrar todos los mensajes para que
cada suscriptor reciba sólo los mensajes que le interesan? Como verás, el
broker tiene varias opciones de filtrado:

OPCIÓN 1: FILTRADO BASADO EN EL TÓPICO


Este filtrado se basa en el asunto o tópico que forma parte de cada mensaje.
El cliente receptor se suscribe al broker por tópicos de interés. A partir de ahí,
el broker se asegura de que el cliente receptor reciba todos los mensajes
publicados en los tópicos suscritos. En general, los tópicos son cadenas con
una estructura jerárquica que permite el filtrado basado en un número
limitado de expresiones.
OPCIÓN 2: FILTRADO BASADO EN EL CONTENIDO
En el filtrado basado en el contenido, el intermediario filtra el mensaje
basándose en un lenguaje de filtrado de contenido específico. Los clientes
receptores se suscriben a las consultas de filtrado de los mensajes que les
interesan. Una desventaja importante de este método es que el contenido del
mensaje debe conocerse de antemano y no puede cifrarse ni modificarse
fácilmente.
OPCIÓN 3: FILTRADO BASADO EN TIPOS
Cuando se utilizan lenguajes orientados a objetos, el filtrado basado en el
tipo/clase de un mensaje (evento) es una práctica habitual. Por ejemplo, un
suscriptor puede escuchar todos los mensajes de tipo Excepción o cualquier
subtipo.

Por supuesto, publicar/suscribir no es la respuesta para todos los casos de


uso. Hay algunas cosas que debes considerar antes de usar este modelo. El
desacoplamiento del publicador y el suscriptor, que es la clave en pub/sub,
presenta algunos desafíos propios. Por ejemplo, hay que saber de antemano
cómo están estructurados los datos publicados. Para el filtrado por temas,
tanto el publicador como el suscriptor deben saber qué tópicos utilizar. Otra
cosa que hay que tener en cuenta es la entrega de los mensajes. El
publicador no puede asumir que alguien está escuchando los mensajes que
se envían. En algunos casos, es posible que ningún suscriptor lea un
determinado mensaje.

Calidad de Servicio (QoS)


Para manejar los desafíos de un sistema pub/sub, MQTT tiene tres niveles de
calidad de servicio (QoS). Se puede especificar fácilmente que un mensaje
sea entregado con éxito desde el cliente al broker o desde el broker a un
cliente. Sin embargo, existe la posibilidad de que nadie se suscriba al tópico
en cuestión. Si esto es un problema, el broker debe saber cómo manejar la
situación. Por ejemplo, el broker HiveMQ MQTT tiene un sistema de plugins
que puede resolver estos casos. Puede hacer que el broker tome medidas o
simplemente registrar cada mensaje en una base de datos para realizar
análisis históricos. Para mantener la flexibilidad del árbol de tópicos
jerárquico, es importante diseñar el árbol de tópicos con mucho cuidado y
dejar espacio para futuros casos de uso. Si se siguen estas estrategias, MQTT
es perfecto para las configuraciones de producción.
Distinción de las colas de mensajes
Hay mucha confusión sobre el nombre MQTT y sobre si el protocolo está
implementado como una cola de mensajes o no. Intentaremos arrojar algo de
luz sobre el tópico y explicar las diferencias. En nuestro último post,
mencionamos que MQTT se refiere al producto MQseries de IBM y no tiene
nada que ver con "cola de mensajes". Independientemente de la procedencia
del nombre, es útil entender las diferencias entre MQTT y una cola de
mensajes tradicional:

● Una cola de mensajes almacena los mensajes hasta que se consumen:


Cuando se utiliza una cola de mensajes, cada mensaje entrante se
almacena en la cola hasta que lo recoge un cliente (a menudo llamado
consumidor). Si ningún cliente recoge el mensaje, éste permanece en
la cola y espera a ser consumido. En una cola de mensajes, no es
posible que un mensaje no sea procesado por ningún cliente, como
ocurre en MQTT si nadie se suscribe a un tópico.
● Un mensaje sólo es consumido por un cliente: Otra gran diferencia es
que en una cola de mensajes tradicional un mensaje sólo puede ser
procesado por un consumidor. La carga se distribuye entre todos los
consumidores de una cola. En MQTT el comportamiento es todo lo
contrario, cada suscriptor que se suscribe al tópico recibe el mensaje.

● Las colas tienen nombre y deben ser creadas explícitamente: Una cola
es mucho más rígida que un tópico. Antes de poder utilizar una cola,
ésta debe ser creada explícitamente con un comando separado. Sólo
después de nombrar y crear la cola es posible publicar o consumir
mensajes. En cambio, los tópicos MQTT son extremadamente flexibles
y pueden crearse sobre la marcha.

Escalabilidad
MQTT Pub/Sub escala mejor que el enfoque tradicional cliente-servidor.
Esto se debe a que las operaciones en el broker pueden ser altamente
paralelas y los mensajes pueden ser procesados de una manera dirigida por
eventos. El almacenamiento en caché de los mensajes y el enrutamiento
inteligente de los mismos suelen ser factores decisivos para mejorar la
escalabilidad. Sin embargo, escalar a millones de conexiones es un reto. Un
nivel tan alto de conexiones puede lograrse con nodos broker agrupados para
distribuir la carga entre más servidores individuales utilizando equilibradores
de carga.

Cliente y broker MQTT


Debido a que MQTT desacopla el publicador del suscriptor, las conexiones de
los clientes siempre son manejadas por un broker. Antes de entrar en los
detalles de estas conexiones, vamos a aclarar lo que entendemos por cliente
y broker.

Cliente
Cuando hablamos de un cliente, casi siempre nos referimos a un cliente
MQTT. Tanto los publicadores como los suscriptores son clientes MQTT. Las
etiquetas de publicador y suscriptor se refieren a si el cliente está
actualmente publicando mensajes o suscrito para recibirlos (la funcionalidad
de publicar y suscribir también puede ser implementada en el mismo cliente
MQTT). Un cliente MQTT es cualquier dispositivo (desde un microcontrolador
hasta un servidor completo) que ejecuta una biblioteca MQTT y se conecta a
un broker MQTT a través de una red. Por ejemplo, el cliente MQTT puede ser
un dispositivo muy pequeño, con recursos limitados, que se conecta a través
de una red inalámbrica y tiene una biblioteca mínima. El cliente MQTT
también puede ser un ordenador típico que ejecute un cliente MQTT gráfico
con fines de prueba. Básicamente, cualquier dispositivo que hable MQTT
sobre una pila TCP/IP puede ser llamado cliente MQTT. La implementación
del cliente del protocolo MQTT es muy sencilla y simplificada. La facilidad de
implementación es una de las razones por las que MQTT es ideal para
dispositivos pequeños. Las bibliotecas de clientes MQTT están disponibles
para una gran variedad de lenguajes de programación. Por ejemplo, Android,
Arduino, C, C++, C#, Go, iOS, Java, JavaScript y .NET. Puedes ver una lista
completa en la wiki de MQTT.

Broker
La contrapartida del cliente MQTT es el broker MQTT. El broker es el corazón
de cualquier protocolo de publicación/suscripción. Dependiendo de la
implementación, un broker puede manejar hasta millones de clientes MQTT
conectados simultáneamente.

El broker es responsable de recibir todos los mensajes, filtrarlos, determinar


quién está suscrito a cada mensaje y enviar el mensaje a estos clientes
suscritos. El broker también mantiene los datos de sesión de todos los
clientes que tienen sesiones persistentes, incluyendo las suscripciones y los
mensajes perdidos (más detalles). Otra responsabilidad del broker es la
autenticación y autorización de los clientes. Normalmente, el broker es
extensible, lo que facilita la autenticación y autorización personalizadas y la
integración en los sistemas backend. La integración es especialmente
importante porque el broker suele ser el componente que se expone
directamente en Internet, maneja muchos clientes y necesita pasar mensajes
a los sistemas de análisis y procesamiento posteriores. Como ya se comentó
en un post anterior, suscribirse a todos los mensajes no es realmente una
opción. En resumen, el broker es el eje central por el que deben pasar todos
los mensajes. Por lo tanto, es importante que el broker sea altamente
escalable, integrable en los sistemas backend, fácil de supervisar y (por
supuesto) resistente a los fallos. HiveMQ cumple estos requisitos mediante el
uso de un procesamiento de red basado en eventos de última generación, un
sistema de extensión abierto y proveedores de monitorización estándar.

Conexión MQTT
El protocolo MQTT se basa en TCP/IP. Tanto el cliente como el broker
necesitan tener una pila TCP/IP.

La conexión MQTT es siempre entre un cliente y el broker. Los clientes nunca


se conectan entre sí directamente. Para iniciar una conexión, el cliente envía
un mensaje CONNECT al broker. El broker responde con un mensaje
CONNACK y un código de estado. Una vez establecida la conexión, el broker
la mantiene abierta hasta que el cliente envía un comando de desconexión o
la conexión se rompe.
Conexión MQTT a través de un NAT
En muchos casos de uso común, el cliente MQTT se encuentra detrás de un
router que utiliza la traducción de direcciones de red (NAT) para traducir de
una dirección de red privada (como 192.168.x.x, 10.0.x.x) a una dirección de
cara al público. Como ya hemos mencionado, el cliente MQTT inicia la
conexión enviando un mensaje CONNECT al broker. Debido a que el broker
tiene una dirección pública y mantiene la conexión abierta para permitir el
envío y recepción bidireccional de mensajes (después del CONNECT inicial),
no hay ningún problema con los clientes que se encuentran detrás de un NAT.

El cliente inicia la conexión con el mensaje CONNECT


Veamos ahora el mensaje de comando MQTT CONNECT. Para iniciar una
conexión, el cliente envía un mensaje de comando al broker. Si este mensaje
CONNECT está mal formado (según la especificación MQTT) o pasa
demasiado tiempo entre la apertura de un socket de red y el envío del
mensaje de conexión, el broker cierra la conexión. Este comportamiento
disuade a los clientes maliciosos que pueden ralentizar el broker. Un cliente
MQTT 3 bondadoso envía un mensaje de conexión con el siguiente contenido
(entre otras cosas):
Nos centraremos en las siguientes opciones:
● ClientId: El identificador de cliente (ClientId) identifica a cada cliente
MQTT que se conecta a un broker MQTT. El broker utiliza el ClientId
para identificar al cliente y el estado actual del mismo.Por lo tanto, este
Id debe ser único por cliente y broker. En MQTT 3.1.1 puedes enviar un
ClientId vacío, si no necesitas que el broker tenga un estado. El
ClientId vacío resulta en una conexión sin ningún estado. En este caso,
la bandera de sesión limpia debe ser establecida en true o el broker
rechazará la conexión.
● Sesión limpia: El indicador de sesión limpia indica al agente si el
cliente desea establecer una sesión persistente o no. En una sesión
persistente (CleanSession = false), el broker almacena todas las
suscripciones para el cliente y todos los mensajes perdidos para el
cliente que se suscribió con una calidad de servicio (QoS) de nivel 1 o
2. Si la sesión no es persistente (CleanSession = true), el broker no
almacena nada para el cliente y purga toda la información de cualquier
sesión persistente anterior.
● Nombre de usuario/contraseña: MQTT puede enviar un nombre de
usuario y una contraseña para la autenticación y autorización del
cliente. Sin embargo, si esta información no está encriptada o con hash
(ya sea por implementación o TLS), la contraseña se envía en texto
plano. Recomendamos encarecidamente el uso de nombres de usuario
y contraseñas junto con un transporte seguro. Los brokers como
HiveMQ pueden autenticar a los clientes con un certificado SSL, por lo
que no es necesario el nombre de usuario y la contraseña.
● Mensaje de testamento: El mensaje de última voluntad es parte de la
función de última voluntad (LWT) de MQTT. Este mensaje notifica a los
demás clientes cuando un cliente se desconecta de forma poco
elegante. Cuando un cliente se conecta, puede proporcionar al broker
una última voluntad en forma de mensaje MQTT y tópicos dentro del
mensaje CONNECT. Si el cliente se desconecta de forma no grata, el
broker envía el mensaje LWT en nombre del cliente. Puedes aprender
más sobre LWT en la parte 9 de esta serie.
● KeepAlive: El keep alive es un intervalo de tiempo en segundos que el
cliente especifica y comunica al broker cuando se establece la
conexión. Este intervalo define el mayor período de tiempo que el
broker y el cliente pueden soportar sin enviar un mensaje. El cliente se
compromete a enviar regularmente mensajes de solicitud PING al
broker. El broker responde con una respuesta PING. Este método
permite a ambos lados determinar si el otro está todavía disponible.
Consulta la parte 10 de esta serie para obtener información detallada
sobre la funcionalidad MQTT keep alive.

Básicamente, esa es toda la información que se necesita para conectarse a


un broker MQTT desde un cliente MQTT 3.1.1. Las bibliotecas individuales
suelen tener opciones adicionales que puedes configurar. Por ejemplo, la
forma en que se almacenan los mensajes en cola en una implementación
específica.

Respuesta del broker con un mensaje CONNACK


Cuando un broker recibe un mensaje CONNECT, está obligado a responder
con un mensaje CONNACK.

El mensaje CONNACK contiene dos entradas de datos:


● El indicador de sesión presente
● Un código de retorno de conexión

Bandera de sesión presente


El indicador de sesión presente indica al cliente si el corredor ya tiene una
sesión persistente disponible de interacciones anteriores con el cliente.
Cuando un cliente se conecta con la sesión limpia establecida como
verdadera, el indicador de sesión presente es siempre falso porque no hay
ninguna sesión disponible. Si un cliente se conecta con Clean Session en
falso, hay dos posibilidades: Si la información de la sesión está disponible
para el clientId. y el corredor ha almacenado la información de la sesión, el
indicador de sesión presente es verdadero. De lo contrario, si el broker no
tiene ninguna información de sesión para el clientId, la bandera de sesión
presente es falsa. Esta bandera fue añadida en MQTT 3.1.1 para ayudar a los
clientes a determinar si necesitan suscribirse a tópicos o si los tópicos están
todavía almacenados en una sesión persistente.

Código de retorno de la conexión


La segunda bandera en el mensaje CONNACK es la bandera de
reconocimiento de conexión. Esta bandera contiene un código de retorno que
indica al cliente si el intento de conexión fue exitoso o no.

Return Code Return Code Response

0 Conexión aceptada

1 Conexión rechazada, versión


de protocolo no aceptable

2 Conexión rechazada,
identificador rechazado
3 Conexión rechazada, servidor
no disponible

4 Conexión rechazada, nombre


de usuario o clave incorrecta

5 Conexión rechazada, sin


autorización

Publicación y Suscripción
Publicación

Un cliente MQTT puede publicar mensajes tan pronto como se conecta a un


broker. MQTT utiliza el filtrado basado en tópicos de los mensajes en el
broker. Cada mensaje debe contener un tópico que el broker puede utilizar
para reenviar el mensaje a los clientes interesados. Normalmente, cada
mensaje tiene una carga útil que contiene los datos a transmitir en formato
de bytes. MQTT es independiente de los datos. El caso de uso del cliente
determina cómo se estructura la carga útil. El cliente emisor (publicador)
decide si quiere enviar datos binarios, datos de texto o incluso XML o JSON
completos.

Un mensaje PUBLISH en MQTT tiene varios atributos que queremos discutir


en detalle:
● Identificador de paquete: El identificador de paquete identifica de
forma exclusiva un mensaje mientras fluye entre el cliente y el agente.
El identificador del paquete sólo es relevante para los niveles de QoS
superiores a cero. La biblioteca del cliente y/o el broker son
responsables de establecer este identificador interno de MQTT.
● Nombre de los tópicos: El nombre de los tópicos es una cadena simple
estructurada jerárquicamente con barras inclinadas como
delimitadores. Por ejemplo, "myhome/livingroom/temperature".
● QoS: Este número indica el nivel de calidad de servicio (QoS) del
mensaje. Hay tres niveles: 0, 1 y 2. El nivel de servicio determina qué
tipo de garantía tiene un mensaje para llegar al destinatario previsto
(cliente o broker).
● Retain Flag: Esta bandera define si el mensaje es guardado por el
broker como el último valor bueno conocido para un tópico
especificado. Cuando un nuevo cliente se suscribe a un tópico, recibe
el último mensaje retenido en ese tópico. Para más detalles sobre los
mensajes retenidos, véase la parte 8 de MQTT Essentials.
● Carga útil: Es el contenido real del mensaje. MQTT es independiente
de los datos. Es posible enviar imágenes, texto en cualquier
codificación, datos encriptados y prácticamente todos los datos en
binario.
● Bandera DUP: La bandera indica que el mensaje es un duplicado y fue
reenviado porque el destinatario previsto (cliente o broker) no acusó
recibo del mensaje original. Esto sólo es relevante para una QoS mayor
que 0. Normalmente, el mecanismo de reenvío/duplicado es manejado
por la biblioteca del cliente MQTT o el broker como un detalle de
implementación. Para más información, parte 6 de MQTT Essentials.

Cuando un cliente envía un mensaje a un broker MQTT para su publicación, el


broker lee el mensaje, acusa recibo del mismo (según el nivel de QoS) y lo
procesa. El procesamiento por parte del broker incluye determinar qué
clientes se han suscrito al tópico y enviarles el mensaje.

El cliente que publica inicialmente el mensaje sólo se preocupa de entregar


el mensaje PUBLISH al broker. Una vez que el broker recibe el mensaje
PUBLISH, es su responsabilidad entregar el mensaje a todos los suscriptores.
El cliente publicador no recibe ninguna información sobre si alguien está
interesado en el mensaje publicado o cuántos clientes han recibido el
mensaje del broker.

Suscripción

Publicar un mensaje no tiene sentido si nadie lo recibe. En otras palabras, si


no hay clientes que se suscriban a los tópicos de los mensajes. Para recibir
mensajes sobre tópicos de interés, el cliente envía un mensaje SUBSCRIBE al
broker MQTT. Este mensaje de suscripción es muy simple, contiene un
identificador de paquete único y una lista de suscripciones.
● Identificador de paquete: El identificador de paquete identifica de
forma única un mensaje mientras fluye entre el cliente y el broker. La
biblioteca del cliente y/o el broker son responsables de establecer este
identificador interno de MQTT.
● Lista de suscripciones: Un mensaje SUBSCRIBE puede contener
múltiples suscripciones para un cliente. Cada suscripción se compone
de un tópico y un nivel de calidad de servicio. El tópico en el mensaje
de suscripción puede contener comodines que hacen posible
suscribirse a un patrón de tópicos en lugar de un tópico específico. Si
hay suscripciones superpuestas para un cliente, el broker entrega el
mensaje que tiene el mayor nivel de calidad de servicio para ese
tópico.

Suback
Para confirmar cada suscripción, el broker envía un mensaje de acuse de
recibo SUBACK al cliente. Este mensaje contiene el identificador de paquete
del mensaje original Subscribe (para identificar claramente el mensaje) y una
lista de códigos de retorno.
● Identificador del paquete: El identificador del paquete es un
identificador único que se utiliza para identificar un mensaje. Es el
mismo que en el mensaje SUBSCRIBE.
● Código de retorno: El broker envía un código de retorno por cada par
de tópicos/QoS que recibe en el mensaje SUBSCRIBE. Por ejemplo, si
el mensaje SUBSCRIBE tiene cinco suscripciones, el mensaje SUBACK
contiene cinco códigos de retorno. El código de retorno reconoce cada
tópico y muestra el nivel de QoS que es otorgado por el broker. Si el
broker rechaza una suscripción, el mensaje SUBACK contiene un
código de retorno de fallo para ese tópico específico. Por ejemplo, si el
cliente no tiene permiso suficiente para suscribirse al tópico o el tópico
está malformado.

Return Code Return Code Response

0 Éxito - Máximo QoS 0

1 Éxito - Máximo QoS 1

2 Éxito - Máximo QoS 2

128 Fallo

Después de que un cliente envíe con éxito el mensaje SUBSCRIBE y reciba el


mensaje SUBACK, obtiene todos los mensajes publicados que coincidan con
un tópico de las suscripciones que contenía el mensaje SUBSCRIBE.

Anulación de la suscripción

La contrapartida del mensaje SUBSCRIBE es el mensaje UNSUBSCRIBE. Este


mensaje elimina las suscripciones existentes de un cliente en el broker. El
mensaje UNSUBSCRIBE es similar al mensaje SUBSCRIBE y tiene un
identificador de paquete y una lista de tópicos.

● Identificador de paquete: El identificador de paquete identifica de


forma única un mensaje mientras fluye entre el cliente y el broker. La
biblioteca del cliente y/o el broker son responsables de establecer este
identificador interno de MQTT.
● Lista de tópicos: La lista de tópicos puede contener múltiples tópicos
de los que el cliente quiere darse de baja. Sólo es necesario enviar el
tópico (sin QoS). El broker desuscribe el tópico, independientemente
del nivel de QoS con el que se suscribió originalmente.
UNSUBACK
Para confirmar la desuscripción, el broker envía un mensaje de acuse de
recibo UNSUBACK al cliente. Este mensaje contiene únicamente el
identificador de paquete del mensaje UNSUBSCRIBE original (para identificar
claramente el mensaje).

Identificador del paquete El identificador del paquete identifica de forma


exclusiva el mensaje. Como ya se ha mencionado, es el mismo identificador
de paquete que aparece en el mensaje UNSUBSCRIBE.

Tras recibir el UNSUBACK del broker, el cliente puede asumir que las
suscripciones del mensaje UNSUBSCRIBE se han eliminado.

Tópicos MQTT
En MQTT, la palabra tópicos se refiere a una cadena UTF-8 que el broker
utiliza para filtrar los mensajes de cada cliente conectado. El tópico consiste
en uno o más niveles de tópicos. Cada nivel de tópicos está separado por una
barra diagonal (separador de niveles de tópicos).

En comparación con una cola de mensajes, los tópicos MQTT son muy
ligeros. El cliente no necesita crear el tópico deseado antes de publicarlo o
suscribirse a él. El broker acepta cada tópico válido sin ninguna inicialización
previa.

Estos son algunos ejemplos de tópicos:


myhome/groundfloor/livingroom/temperature
USA/California/SanFrancisco/SiliconValley
5ff4a2ce-e485-40f4-826c-b1a5d81be9b6/status
Germany/Bavaria/car/2382340923453/latitude

Tenga en cuenta que cada tópico debe contener al menos 1 carácter y que la
cadena de tópicos permite espacios vacíos. Los tópicos distinguen entre
mayúsculas y minúsculas. Por ejemplo, micasa/temperatura y
Micasa/temperatura son dos tópicos diferentes. Además, la barra diagonal
sola es un tópico válido.

Comodines MQTT
Cuando un cliente se suscribe a un tópico, puede suscribirse al tópico exacto
de un mensaje publicado o puede utilizar comodines para suscribirse a varios
tópicos simultáneamente. Un comodín sólo puede utilizarse para suscribirse
a tópicos, no para publicar un mensaje. Hay dos tipos diferentes de
comodines: de un solo nivel y de varios niveles.

De un solo nivel: +
Como su nombre indica, un comodín de un nivel sustituye a un nivel de
tópicos. El símbolo + representa un comodín de un nivel en un tópico.

Cualquier tópico coincide con un tópico con comodín de un nivel si contiene


una cadena arbitraria en lugar del comodín. Por ejemplo, una suscripción a
myhome/groundfloor/+/temperature puede producir los siguientes
resultados:
Multi-Nivel: #
El comodín multinivel cubre muchos niveles de tópicos. El símbolo de hash
representa el comodín multinivel en el tópico. Para que el broker determine
qué tópicos coinciden, el comodín multinivel debe colocarse como último
carácter del tópico y estar precedido por una barra diagonal.

Cuando un cliente se suscribe a un tópico con un comodín multinivel, recibe


todos los mensajes de un tópico que comienza con el patrón antes del
carácter comodín, sin importar la longitud o profundidad del tópico. Si
especifica sólo el comodín multinivel como tópico (#), recibe todos los
mensajes que se envían al broker MQTT. Si espera un alto rendimiento, la
suscripción sólo con un comodín multinivel es un anti-patrón (vea las
mejores prácticas más abajo).

Tópicos MQTT que comienzan con $


Generalmente, puede nombrar sus tópicos MQTT como desee. Sin embargo,
hay una excepción: Los tópicos que comienzan con el símbolo $ tienen un
propósito diferente. Estos tópicos no forman parte de la suscripción cuando
se suscribe al comodín multinivel como tópico (#). Los tópicos con el símbolo
$ están reservados para las estadísticas internas del broker MQTT. Los
clientes no pueden publicar mensajes en estos tópicos. Por el momento, no
existe una estandarización oficial para estos tópicos. Comúnmente, $SYS/ se
utiliza para toda la información siguiente, pero las implementaciones del
broker varían. Una sugerencia para tópicos $SYS está en el wiki GitHub de
MQTT. Aquí hay algunos ejemplos:

$SYS/broker/clientes/conectados
$SYS/broker/clientes/desconectados
$SYS/broker/clientes/total
$SYS/broker/mensajes/enviados
$SYS/broker/uptime

Resumen de tópicos de MQTT


Estos son los fundamentos de los tópicos de los mensajes MQTT. Como
puede ver, los tópicos MQTT son dinámicos y proporcionan una gran
flexibilidad. Cuando usas comodines en aplicaciones del mundo real, hay
algunos desafíos que debes tener en cuenta. Hemos recopilado las mejores
prácticas que hemos aprendido al trabajar extensamente con MQTT en varios
proyectos y siempre estamos abiertos a sugerencias o a una discusión sobre
estas prácticas. Utiliza los comentarios para iniciar una conversación, haznos
saber tus mejores prácticas o si no estás de acuerdo con alguna de las
nuestras.

Mejores prácticas de MQTT


● Nunca utilice una barra diagonal inicial: En MQTT se permite el uso
de una barra oblicua. Por ejemplo, /myhome/groundfloor/livingroom.
Sin embargo, la barra oblicua inicial introduce un nivel de tópicos
innecesario con un carácter cero al frente. El cero no proporciona
ningún beneficio y a menudo conduce a la confusión.
● No utilice nunca espacios en un tópico: El espacio es el enemigo
natural de todo programador. Cuando las cosas no van como deberían,
los espacios hacen mucho más difícil leer y depurar tópicos. Al igual
que con las barras inclinadas, sólo porque algo esté permitido, no
significa que deba usarse. UTF-8 tiene muchos tipos diferentes de
espacios en blanco, estos caracteres poco comunes deben ser
evitados.
● Mantenga los tópicos de MQTT cortos y concisos: Cada tópico se
incluye en cada mensaje en el que se utiliza. Haz que tus tópicos sean
lo más cortos y concisos posible. Cuando se trata de dispositivos
pequeños, cada byte cuenta y la longitud de los tópicos tiene un gran
impacto.
● Utilice sólo caracteres ASCII, evite los caracteres no imprimibles:
Como los caracteres UTF-8 que no son ASCII suelen mostrarse de
forma incorrecta, es muy difícil encontrar errores tipográficos o
problemas relacionados con el juego de caracteres. A menos que sea
absolutamente necesario, recomendamos evitar el uso de caracteres
no ASCII en un tópico.
● Incluir un identificador único o el ID de cliente en el tópico: Puede
ser muy útil incluir el identificador único del cliente publicador en el
tópico. El identificador único en el tópico ayuda a identificar quién
envió el mensaje. El identificador incrustado puede utilizarse para
reforzar la autorización. Sólo un cliente que tenga el mismo ID de
cliente que el ID en el tópico puede publicar en ese tópico. Por
ejemplo, un cliente con el ID de cliente1 puede publicar en
cliente1/estado, pero no puede publicar en cliente2/estado.
● No suscribirse a #: A veces, es necesario suscribirse a todos los
mensajes que se transfieren a través del broker. Por ejemplo, para
persistir todos los mensajes en una base de datos. No te suscribas a
todos los mensajes de un broker utilizando un cliente MQTT y
suscribiéndote a un comodín de varios niveles. Con frecuencia, el
cliente suscriptor no es capaz de procesar la carga de mensajes que
resulta de este método (especialmente si tiene un rendimiento
masivo). Nuestra recomendación es implementar una extensión en el
broker MQTT. Por ejemplo, con el sistema de plugins de HiveMQ
puedes engancharte al comportamiento de HiveMQ y añadir una rutina
asíncrona para procesar cada mensaje entrante y almacenarlo en una
base de datos.
● No olvides la extensibilidad: Los tópicos son un concepto flexible y no
es necesario preasignarlos de ninguna manera. Sin embargo, tanto el
publicador como el suscriptor deben conocer los tópicos. Es
importante pensar en cómo se pueden ampliar los tópicos para
permitir nuevas funciones o productos. Por ejemplo, si su solución de
hogar inteligente añade nuevos sensores, debería ser posible añadirlos
al árbol de tópicos sin cambiar toda la jerarquía de tópicos.
● Utilice tópicos específicos, no generales: Cuando nombres tópicos,
no los uses de la misma manera que en una cola. Diferencie sus
tópicos tanto como sea posible. Por ejemplo, si tienes tres sensores en
tu salón, crea tópicos para micasa/salón/temperatura,
micasa/salón/brillo y micasa/salón/humedad. No envíe todos los
valores sobre myhome/livingroom. El uso de un único tópico para todos
los mensajes es un patrón anti. La nomenclatura específica también le
permite utilizar otras características de MQTT, como los mensajes
retenidos.

Utilizar MQTT en Thingworx


Para lograr establecer una conexión MQTT con Thingworx necesitamos los
elementos principales, es decir, un cliente MQTT y un broker.

Broker
Como broker utilizaremos uno gratuito de acceso público llamado HiveMQ
(http://www.hivemq.com/demos/websocket-client/). En este link
encontraremos las configuraciones indicadas en la sección Conexión MQTT-
cliente MQTT - Connect, tales como Username, KeepAlive, CleanSession, etc.
En el link https://www.hivemq.com/public-mqtt-broker/ se encuentran las
características del broker que luego usaremos para establecer la conexión
entre el broker público hiveMQ y el cliente MQTT en Thingworx:

Cliente MQTT
Si recordamos, el cliente MQTT no permite publicar y suscribirse a tópicos
para enviar y recibir mensajes MQTT. Para ello necesitamos instalar una
extensión en la plataforma Thingworx.

Importar extensión
Para poder tener acceso a MQTT desde Thingworx, es necesario importar la
extensión de MQTT, esta extensión permite configurar clientes MQTT que pueden
suscribirse y publicar en los tópicos del broker.

Importar extensión
1.- En la pantalla de inicio de Composer, busca en la barra lateral izquierda el ícono
de Import/export (2 flechas).

2.- Seleccionar la opción de importar.


3.- Luego de seleccionar, se desplegará una ventana emergente tal como la
siguiente imágen. En las opciones de importar, selecciona Extensión.
4.- Dale click a Browse para buscar y seleccionar el archivo extensión MQTT, el cual
tiene un nombre similar a MED-61334-CD-092_F000_MQTT-Extensions-3-0-0.zip.
Para conseguir este archivo, pídeselo al administrador de la cuenta PTC support
(https://www.ptc.com/en/support).

5.- Dale click a Validate para verificar que todo está en orden. en la misma ventana
recibirás un mensaje que indica si está correcto o hay algún error. Si está correcto,
dale click Import.
6.- Para verificar que la extensión está instalada y ver su información puedes
dirigirte al ícono de Manage en la barra lateral izquierda. Al final de las opciones
encontrarás Installed Extensions.

7.- De esta manera podrás acceder a la información de la extensión MQTT.


Configuración de extensión MQTT
Una vez importada correctamente la extensión MQTT, tendremos acceso a nuevos
Things Templates tales como MQTT, MQTT connector, MQTT subscriber. Para los
siguientes ejemplos utilizaremos la Thing Template MQTT que permite configurar
un cliente MQTT que puede publicar y suscribirse.

1.- El primer paso es crear un thing y escoger MQTT como base Thing Template.

2.- Para mantener cierto orden, nombraremos a la thing como MQTT_client_XX,


donde XX corresponde a las iniciales de cada usuario. Luego, guardamos los datos
para crear la thing.
3.- Una vez creada nuestra thing, procedemos a configurar para que se comunique
con el broker público de HiveMQ. Para ello, hacemos click en la pestaña
Configuration. En la sección JDBC Settings buscamos la opción serverName y
colocamos broker.hivemq.com, y en serverPort colocamos 1883. Luego, agregamos
los tópicos usando +Add en la sección Mapping. Agregue los tópicos
twx/status/signal_XX y twx/status/publish_XX donde cada uno reemplaza XX
con sus iniciales. Recuerde sustituir las iniciales XX o JZ por las suyas, sino podría
recibir mensajes de otros usuarios. Note que twx/status/signal_XX esta
configurado solo como suscriptor y twx/status/publish_XX solo como publicador.
Adicionalmente, necesita darle un nombre a la variable donde se alojará la
información recibida. Recomendamos usar la última cadena de caracteres del
tópico como nombre.

5.- Luego, nos dirigimos a la pestaña Properties and Alerts de la Thing y creamos
las propiedades nombradas anteriormente en la configuración. Se debe utilizar el
mismo nombre asignado a los tópicos.
Pruebas de conectividad
Teniendo ya configurado el cliente MQTT en Thingworx, el siguiente paso es realizar
pruebas de conectividad entre Thingworx y el broker MQTT. Para ello, utilizaremos
un cliente MQTT integrado al broker de HiveMQ que nos permitirá realizar pruebas
de conectividad de forma muy sencilla y eficiente.

1.- El primer paso será conectarnos al broker, no es necesario agregar ningún dato
en la configuración sino simplemente dar click a Connect.

2.- Al conectarnos correctamente al broker el punto rojo cambiará a verde, y las


pestañas de Publish y Subscriptions desplegarán sus opciones.
3.- En la pestaña de Subscriptions ponemos el tópico twx/status/signal_XX donde
cada uno reemplaza XX con sus iniciales. En la pestaña de Publish escribiremos el
mismo tópico e incluiremos un mensaje. Si todo está en orden, al darle click a
Publish recibiremos el mensaje en la pestaña Messages tal como aparece en la
siguiente imagen.
4.- Revisamos en las propiedades de nuestra Thing para verificar que Thingworx
también está correctamente conectado al broker de HiveMQ. De esta manera
hemos logrado utilizar el cliente MQTT en Thingworx como suscriptor.

5.- También podemos usar el cliente MQTT como publicador. Nos dirigimos a la
interfaz de cliente MQTT HiveMQ y nos suscribimos al tópico
twx/status/publish_XX. Luego, volvemos a nuestra Thing en Thingworx y editamos
la propiedad publish_test dando click en Set_value (por ejemplo ‘Hello world’). Si
revisamos el cliente MQTT de HiveMQ, veremos que se ha recibido el valor editado
en Thingworx.
Resumen
Enhorabuena. Ha completado con éxito la guía Protocolo MQTT: concepto y
aplicaciones.

Ha aprendido a utilizar el Protocolo MQTT para:


● Conceptos básicos del protocolo MQTT para su correcta aplicación,
utilizando las mejores prácticas.
● Instalar y configurar clientes MQTT en Thingworx.
● Recibir mensajes MQTT en Thingworx a través del cliente suscriptor.
● Enviar mensajes MQTT desde Thingworx a través del cliente publicador.

También podría gustarte