Book Image

MQTT Essentials - A Lightweight IoT Protocol

5 (1)
Book Image

MQTT Essentials - A Lightweight IoT Protocol

5 (1)

Overview of this book

This step-by-step guide will help you gain a deep understanding of the lightweight MQTT protocol. We’ll begin with the specific vocabulary of MQTT and its working modes, followed by installing a Mosquitto MQTT broker. Then, you will use best practices to secure the MQTT Mosquitto broker to ensure that only authorized clients are able to publish and receive messages. Once you have secured the broker with the appropriate configuration, you will develop a solution that controls a drone with Python. Further on, you will use Python on a Raspberry Pi 3 board to process commands and Python on Intel Boards (Joule, Edison and Galileo). You will then connect to the MQTT broker, subscribe to topics, send messages, and receive messages in Python. You will also develop a solution that interacts with sensors in Java by working with MQTT messages. Moving forward, you will work with an asynchronous API with callbacks to make the sensors interact with MQTT messages. Following the same process, you will develop an iOS app with Swift 3, build a website that uses WebSockets to connect to the MQTT broker, and control home automation devices with HTML5, JavaScript code, Node.js and MQTT messages
Table of Contents (16 chapters)
MQTT Essentials - A Lightweight IoT Protocol
Credits
About the Author
Acknowledgment
About the Reviewer
www.PacktPub.com
Customer Feedback
Dedication
Preface

Publishing messages


We will use the mosquitto_pub command-line utility included in Mosquitto to generate a simple MQTT client that publishes a message to a topic. Open a Terminal in macOS or Linux, or a Command Prompt in Windows, go to the directory in which Mosquitto is installed and run the following command:

mosquitto_pub -V mqttv311 -t sensors/drone01/altitude -m  "10 f" -d

The previous command will create an MQTT client that will establish a connection with the local MQTT server and then will make the client publish a message to the topic specified after the -t option: sensors/drone01/altitude. We specify the payload for the message after the -m option: "10 f". We specify the version of the MQTT protocol that we want to use when the client establishes the connection with -V mqttv311. This way, we indicate the MQTT server that we want to use MQTT version 3.1.1. We specify the -d option to enable debug messages that will allow us to understand what happens under the hoods. We will analyze additional options for the connection and the publication later.

The Terminal or Command Prompt window will display debug messages similar to the following lines. Take into account that the generated ClientId will be different from the one shown after Client:mosqpub/5303-Gastons-Ma. After publishing the message, the client disconnects.

Client mosqpub/5308-Gastons-Ma sending CONNECT
Client mosqpub/5308-Gastons-Ma received CONNACK
Client mosqpub/5308-Gastons-Ma sending PUBLISH (d0, q0, r0, m1, 'drones/altitude', ... (5 bytes))
Client mosqpub/5308-Gastons-Ma sending DISCONNECT

Now, we will use the MQTT.fx GUI utility to generate another MQTT client that publishes another message to the same topic, sensors/drone01/altitude. Follow the next steps:

  1. Go to the MQTT.fx window in which you established a connection and subscribed to a topic.

  2. Click Publish and enter sensors/drone01/altitude in the dropdown at the left-hand side of the Publish button.

  3. Enter the following text in the textbox below the Publish button: 20 f, as shown in the following screenshot:

  4. Then, click the Publish button. MQTT.fx will publish the entered text to the specified topic.

In case you don't want to work with the MQTT.fx utility, you can run another mosquitto_pub command to generate another MQTT client that publishes a message to the topic. You just need to open another Terminal in macOS or Linux, or another Command Prompt in Windows, go to the directory in which Mosquitto is installed and run the following command.

mosquitto_pub -V mqttv311 -t sensors/drone01/altitude -m "20 f"

Now, go back to the Terminal or Command Prompt window in which you executed the mosquitto_sub command and subscribed to the sensors/drone01/atitude topic. You will see lines similar to the following ones:

Client mosqsub/5532-Gastons-Ma received PUBLISH (d0, q0, r0, m0, 'sensors/drone01/altitude', ... (4 bytes))
10 f
Client mosqsub/5532-Gastons-Ma received PUBLISH (d0, q0, r0, m0, 'sensors/drone01/altitude', ... (4 bytes))
20 f

If we clean up the debug messages that start with the Client prefix, we will see just the next two lines. These lines show the payloads for the two messages that we received as a result of our subscription to the sensors/drone01/altitude topic.

10 f
20 f

Go to the MQTT.fx window and click Subscribe. You will see 2 at the right-hand side of the title for the topic filter used to subscribe in the panel located at the left-hand side of the window. MQTT.fx is telling you that you have received two messages in the sensors/drone01/altitude topic. Click on this panel and MQTT.fx will display all the received messages at the right-hand side of the panel. MQTT.fx will display a number at the right-hand side of each message to specify the message number since we started the subscription to the topic filter. Click on each message and MQTT.fx will display the QoS level for the message (0), the date and time that it was received and the payload for the message in the default plain string format. The following picture shows the payload for the second message that has been received by the subscriber generated by MQTT.fx.

We created two publishers and each of them published a message to the same topic: sensors/drone01/altitude. The two subscribers for this topic received both messages. Now, we will understand what happens under the hoods when a client publishes a message to a topic.

The MQTT client that has already established a connection sends a PUBLISH packet to the MQTT server with a header that includes the following fields and flags. We want to understand the meaning of these fields and flags because we will be able to specify some of their values when we work with MQTT tools and MQTT client libraries.

  • PacketId: If the QoS level is equal to 0, the value for this field will be 0 or it won't be present. In case the QoS level is equal to 1 or 2, the packet identifier will have a number value to identify the packet and make it possible to identify the responses related to this packet.

  • Dup: If the QoS level is equal to 0, the value for this field will be 0. In case the QoS level is equal to 1 or 2, the MQTT client library or the MQTT server can resend a message that was previously published by the client when the subscribers haven't ackowledged the first message. Whenever there is an attempt to resend a message that has already been published, the value for the Dup flag must be 1 or true.

  • QoS: Specifies the QoS level for the message. We will dive deep on the quality of service level for the messages and their relationship with many other flags later. So far, we have been working with QoS level 0.

  • Retain:If the value for this flag is set to 1 or true, the MQTT server will store the message with its specified QoS level. Whenever new MQTT clients subscribers to a topic filter that matches the topic for the stored or retained message, the last stored message for this topic will be sent to the new subscriber. If the value for this flag is set to 0 or false, the MQTT server won't store the message and won't replace a retained message with the same topic in case there is one message retained for this topic.

  • TopicName: A string with the topic name to which the message must be published. Topic names have a hierarchy structure where slashes (/) are used as delimiters. In our examples, the value for TopicName was "sensors/drone01/altitude". We will analyze best practices for topic names later.

Tip

The payload contains the actual message that the MQTT client wants the MQTT server to publish. MQTT is data agnostic, and therefore, we can send any binary data and we don't have restrictions such as those imposed by JSON or XML. Of course, we can use these or others to organize the payloads if we wish. In our examples, we sent a string that included a number that represented the altitude followed by a space and an "f" that indicates the unit of measure is feet.

The MQTT server will read a valid PUBLISH packet and it will respond with a packet only for QoS levels greater than 0. In case the QoS level is 0, the MQTT will not respond. The MQTT server will determine all the subscribers whose subscribed topic matches the topic name specified for the message and the server will publish the message to these clients.

The following diagram shows the interaction between an MQTT client and an MQTT server to publish a message with a QoS level of 0.

The other QoS levels have a different flow with additional interaction between the publisher and the MQTT server and increased overheads that we will analyze later.