Back to all

MQTT Publish, Subscribe and Unsubscribe 101

Picture that you are getting back home from a vacation trip. What would cheer you up after a long road? A cup of freshly brewed coffee! And you can have it ready and waiting for you as soon as you open your entrance door. For this, you only need to launch your coffee maker using your smart home app. It will take just a few clicks to make it happen and get a cup of a tasty drink right up to your arrival. However, underneath this lies a complex MQTT publish-subscribe communication between your smartphone and the coffee maker in your smart home system. 

The same thing works in other IoTs such as security systems, factory equipment, wearable health monitors, etc. What does this look like? This is what we’re going to explain in this article. So, buckle up to learn what the MQTT publish-subscribe model is and how remote IoT devices use it to exchange information. 

MQTT publish-subscribe model explained

All in all, the concept of the MQTT publish-subscribe pattern or simply MQTT pub-sub includes three types of parties: 

  • publisher – a client (device) that posts information onto a self chosen topic.
  • MQTT broker – a party that receives packets from publishers, checks for settings, and then forwards them to subscribers. Learn more about all steps that the broker has to complete.
  • subscriber – a client (device) that is interested in the information on a certain topic.

At first glance, everything looks clear since one client publishes, and the other client receives. However, the publisher does not send information directly to the subscriber. 😳

In the pub-sub MQTT, clients talk to each other through an MQTT broker. We’ve already blogged about the MQTT client and broker connection.

MQTT Subscribe, Publish, Unsubscribe

So, in our coffee maker example, the MQTT communication looks as follows:

Publisher MQTT broker Subscriber schema
MQTT client: Smartphone (publisher) -> MQTT broker -> MQTT client: Coffee maker (subscriber)

At the same time, your smartphone can be a subscriber if you get information about the temperature in your home from the temperature sensors. In this case, the MQTT pub-sub connection looks as follows:

Subscriber MQTT Broker Publisher overview
MQTT client: Smartphone (subscriber) -> MQTT broker -> MQTT client: Temperature sensor (publisher)

An IoT system usually contains multiple devices. How can you understand which ones of them are publishers or subscribers? The MQTT broker comes into play here.

To test our Pro Mosquitto MQTT broker, sign up for a free 14-day trial here!

MQTT pub-sub message flow

A publisher sends messages on a specific topic to an MQTT broker, which forwards them to a client or clients that are subscribed to this topic. Each topic can only have one publisher but multiple subscribers.

What are MQTT topics?

An MQTT topic is a string (only UTF-8 characters are allowed, except “<”, “>”, “$”) that allows the MQTT broker to identify proper publishers and subscribers to send messages. 

  • The client that is interested in sending messages publishes them on a certain topic.
  • The client that is interested in a certain topic subscribes to it and starts receiving messages published on this topic.

MQTT topics can contain one or several levels, separated by a forward slash, for example:

myhome/kitchen/coffeemaker
myhome/kitchen/sensor/temperature

MQTT topics prerequisites

  • An MQTT topic must contain at least one character.
  • An MQTT topic is case-sensitive. This means that myhome/kitchen/coffeemaker and myhome/Kitchen/Coffeemaker are different topics.
  • Clients can use wildcards (special characters) in an MQTT topic to subscribe to multiple MQTT topics. We will deal with them later.

To learn more about MQTT topics and wildcards, check out this guide.

What are MQTT messages?

An MQTT message is the data sent from the publisher and received by the subscriber. The MQTT message format can be:

  1. Fixed header, for example, CONNACK
  2. Fixed header and variable header, for example, PUBACK
  3. Fixed header, variable header, and payload, for example, PUBLISH

Note: The fixed header consists of two fields: the control field and the variable length message field. We won’t focus on this, but if you are interested in the MQTT protocol message structure, check out this guide.

So, what if a publisher sends a message for a topic which no client is subscribed? The MQTT broker should resolve this. Actually, the role of the MQTT broker in the MQTT pub-sub model is crucial. Let’s talk more about this.

MQTT broker in MQTT publish and subscribe model

The MQTT broker is a hub for communication between clients. It obtains messages from publishers and distributes them to the clients based on the topics they are subscribed to. This allows us to keep the workload balanced and maintain the linear growth of the connection count if the number of clients increases. 

However, when choosing an MQTT broker, it’s not the number of clients you should consider, but the traffic load, i.e. the volume of data the clients send per second. A hundred clients sending messages with large attached data (Payload) every few seconds would create a larger workload than a thousand clients sending smaller messages every minute.

Mosquitto MQTT broker is deemed the most downloadable and probably efficient broker worldwide. With it, you can set up MQTT communication between apps, sensors, and versatile devices. The open source version of the Mosquitto broker is a good choice for your personal projects. At the same time, for commercial purposes, it’s better to use an even more reliable and secure version of this popular MQTT broker – Pro Edition for Mosquitto. It embodies the best you can get with Mosquitto plus the MQTT High Availability, optimized performance, fail-safe, etc. Besides, you can choose the hosting option for your MQTT broker: either cloud or on-premises.

We’ll use Mosquitto below to demonstrate the MQTT publish and subscribe examples. You can also try it out absolutely for free with a 14-day trial

Now, let’s see how all this MQTT pub-sub thing looks in action.

To test our Pro Mosquitto MQTT broker, sign up for a free 14-day trial here!

MQTT subscribe to a topic

We start with subscription since it’s required for the MQTT broker to forward messages to the clients that are subscribed for a topic or topics. To establish an MQTT connection between a client (both subscriber and publisher) and a broker, the client sends a CONNECT request and receives a CONNACK response packet. We’ve covered this in our MQTT Connection Beginners Guide.  

MQTT subscribe

Once the connection is established, the client sends a SUBSCRIBE MQTT packet with the topics of interest to the broker. The packet contains two values: 

  • packetId – Unique packet identifier that is set by the client library and the MQTT broker
  • subscription – a topic and a QoS level to subscribe for. The SUBSCRIBE packet can include multiple subscriptions.

Dive deeper into the essence of MQTT packets here.

MQTT subscribe example

packetID0014
qos10
topic1kitchen/sensor/temperature
qos21
topic2kitchen/sensor/humidity
qos32
topic3kitchen/coffeemaker

MQTT Quality of Service for the messages

The pub-sub message delivery process in MQTT has three levels of Quality of Service (QoS):

  • QoS0 – the default level of quality of service that does not guarantee the delivery of the message. The publisher sends the message to the MQTT broker, not more than once, and the broker does not acknowledge the receipt of it. You can use this level when you can accept the message loss. 
  • QoS1 – the quality of service level that guarantees the delivery of the message. The publisher sends the message more than once until the MQTT broker acknowledges the receipt of it. You can use this level when the message must be delivered and you don’t have a problem with the subscriber receiving the message more than once.
  • QoS2 – the quality of service level that guarantees the processing of the message only once. The publisher sends the message and stores it until a double handshake between the sender and receiver has accomplished a s.c. double handshake to acknowledge receipt of it. You can use this level when the message must be processed without any duplicates.

To learn about this topic in detail, check out our article on MQTT QoS levels.

To test our Pro Mosquitto MQTT broker, sign up for a free 14-day trial here!

MQTT subscribe wildcards

In Mosquitto, two wild cards are available to enable the client’s subscription to multiple MQTT topics:

  • + (plus sign) – to match a single level of hierarchy.
  • # (number sign) – to match all levels of hierarchy after #.
+/sensor/temperature
SupportsDoes not support
kitchen/sensor/temperature
bathroom/sensor/temperature
bedroom/sensor/tempera
ture
kitchen/sensor/humidity
kitchen/coffeemaker
kitchen/sensor/temperature/backup
kitchen/#
SupportsDoes not support
kitchen/sensor/temperature
kitchen/sensor/humidity
kitchen/coffeemaker
bathroom/sensor/humidity
bedroom/sensor/temperature

You can only use wildcards in topic filters; hence they are meant for subscribing to topics not publishing messages.

MQTT subscribe – successful or not?

Since the MQTT broker is the first recipient of the published message, it acknowledges the SUBSCRIBE packets via responding with a SUBACK packet to the subscriber. The SUBACK packet contains the packetId and return codes:

  • 0 – Success-Maximum for QoS0
  • 1 – Success-Maximum for QoS1
  • 2 – Success-Maximum for QoS2
  • 128 – Failure

MQTT SUBACK packet example

packetID0014
returnCode1128
returnCode22
returnCode3     3

If the subscription is successful, the MQTT broker will forward the published messages to the clients subscribed to the topic.

MQTT unsubscribe from a topic

To unsubscribe from one or multiple topics, a client sends the UNSUBSCRIBE packet that contains a packetId and a list of topics.

MQTT unsubscribe example

packetID0014
topic4kitchen/sensor/temperature
topic4kitchen/sensor/humidity
topic2kitchen/coffeemaker

We’re done with subscribing our clients to topics. Now, we can publish messages to the MQTT broker and this is what it looks like.

To test our Pro Mosquitto MQTT broker, sign up for a free 14-day trial here!

MQTT publish a message

Just a reminder, publishers can be subscribers and subscribers can be publishers (in case if a subscriber is a publisher for another topic) – this is called bidirectional publishing. In our example with a coffeemaker, your mobile app is a publishing client that sends a message to the coffeemaker. The coffeemaker becomes a publisher once it sends a message that your coffee is ready. 

Again, the information exchange between a publishing client and the MQTT broker starts with the connection. Once it’s successful, the publisher can send messages to the broker, which, in turn, forwards messages to the clients subscribed to the message topic. For this, the client sends a PUBLISH MQTT packet with the following values: 

  • packetId – Unique packet identifier that is set by the client library and the MQTT broker.
  • topicName – the topic string. 
  • qos – the level of quality of service for the message delivery.
  • retainFlag – if true, then the message will be retained. This makes sense when a subscribed device cannot wait until the next message is published, for example, a car door sensor. 
  • payload – encryption of application-specific data on the application level (a message).
  • dupFlag – if true, then the message duplicate was resent.

MQTT publish example

Here is what the PUBLISH packet looks like in real life.

packetID0014
topicNamekitchen/coffeemaker
qos2
retainFlagfalse
PayloadHello, this is a message.
dupFlagfalse

MQTT publish acknowledgement

Different levels of QoS have different acknowledgement mechanisms. For QoS0, the MQTT broker forwards the published message to the subscribers without any acknowledgement from their side. This is why the QoS0 is often called ‘fire and forget’.

QoS1 publish acknowledgement

For the messages with the QoS1 level, the subscribers send a publish acknowledge packet – PUBACK. If they don’t, the MQTT broker keeps sending PUBLISH packets with the dupFlag parameters set to TRUE.

QoS2 publish acknowledgement

For the highest level of MQTT quality of service, the publish acknowledgment is slightly trickier. Once the subscriber receives the published message, it replies with a PUBREC packet. Until the MQTT broker receives PUBREC, it keeps sending PUBLISH packets with the dupFlag parameters set to TRUE.

Simultaneously, once the broker gets the PUBREC and forwards it to the publisher, the latter responds with a PUBREL packet. Again, the broker gets the PUBREL and forwards it to the subscriber which replies with another packet – PUBCOMP. With the receipt of the PUBCOMP packet by the publisher, the packet id becomes available for reuse.

Can the MQTT publisher know whether the published topic has subscribers?

In the older version of MQTT (up to v5), the client never knows about the subscribers of the published messages. However, in MQTT v5, this is enabled for two QoS levels: QoS1 and QoS2. The MQTT broker sends a PUBACK or PUBREC packet with the information about no subscribers.

mosquitto_pub and mosquitto_sub examples

Let’s wrap up our MQTT pub-sub tutorial with a brief intro to the simple client utilities that you get within the Mosquito package:

  • Mosquitto_pub – to publish a single message on a topic.
  • Mosquitto_sub – to subscribe to topics.

Thus, these tools are quite handy if you need to test clients’ publishing and subscribing. We won’t dive into details of mosquitto_pub and mosquitto_sub here, you can learn them in the Mosquitto manual on the Cedalo website. What we demonstrate here are examples of how they work. 

mosquitto_pub example

Since we’ve been talking about our coffee maker throughout the article, let’s check out how you can publish a message to turn it on:

mosquitto_pub -h localhost -t kitchen/coffeemaker -m "on" -q 1
  • -h – the host to connect to
  • -t – the topic of a message
  • -m – the message
  • -q – the quality of service

The coffeemaker example is not that widespread, so let’s see the more common one. We’ll publish temperature information:

mosquitto_pub -h localhost -t kitchen/sensor/temperature -m 22 -q 2

mosquitto_sub example

Let’s subscribe to the status of the coffee maker:

mosquitto_sub -h localhost -t kitchen/coffeemaker -q 1

Or, here is an example of subscribing to all sensors located in the kitchen:

mosquitto_sub -t kitchen/sensors/+ -q 2

To see more examples, check out this awesome guide on using these Mosquitto client tools.

To test our Pro Mosquitto MQTT broker, sign up for a free 14-day trial here!

MQTT publish and subscribe key takeaways

Consequently, the MQTT publish/subscribe model may remind you of the traditional client-server communication pattern, where clients exchange information directly with the server. In MQTT, all devices are clients, and they talk to each other via the MQTT broker. So, this is the central element that the entire IoT system rests on. MQTT brokers filter the clients’ published messages by topics and distribute them to the clients that are subscribed to the respective topics. 

Eventually, the proper choice of the MQTT broker will let you optimize the communication of all devices in your system. So, choose wisely 🙂

Click to rate this post!
[Total: 3 Average: 3.7]
About the author
Zakhar Yung

Zakhar Yung

Content Manager

Zakhar is a content manager at Coupler.io, tasked with the important role of ensuring that readers love and enjoy the content created by the company. With over 5 years of experience as a skilled writer in the SaaS industry, Zakhar can craft texts that resonate with the audience's queries.

Despite not being a developer, Zakhar sees this as an advantage in effectively explaining complex technical concepts to the readers using simple and accessible language. Zakhar's content expertise spans various areas, such as working with REST APIs, data automation, reporting and analytics, MQTT, email testing, and more.

Newsletters icon

Subscribe for monthly updates