Post

MQTT with Raspberry Pi

MQTT with Raspberry Pi

What it is MQTT?

MQTT (Message Queuing Telemetry Transport) is a lightweight messaging protocol designed for efficient communication between devices in constrained environments, commonly used in IoT (Internet of Things) applications.

  • To get Startet with RPi and MQTT we will need:
    • An MQTT broker is a server that acts as an intermediary for MQTT communication, facilitating message exchange between devices by receiving, routing, and delivering messages to subscribed clients.
    • Any device or software component that establishes a connection to an MQTT service using the TCP/IP protocol can be referred to as an MQTT client.

Related MQTT Scripts are here

Why MQTT for IoT?

MQTT is popular for IoT due to its lightweight nature, minimal bandwidth usage, and support for low-power devices, making it ideal for communication in resource-constrained environments.

Find the code used on this Post here.

MQTT Setup with Raspberry Pi

This is our to do list for the project:

  • MQTT
    • Install a MQTT Client
    • Install a MQTT Broker
    • Testing the MQTT Broker
    • Test the Connection
  • Node-Red
  • Home Assistant
  • PostMan

Install MQTT Client

There are many options - I like MQTTX which is free.

Which you can install in any platform (and even SelfHost MQTTX with Docker).

Here is how to install MQTTx with Flatpak:

1
flatpak install flathub com.emqx.MQTTX
  • MQTT
    • Install a MQTT Client
    • Install a MQTT Broker
    • Testing the MQTT Broker
    • Test the Connection

Install MQTT Broker

For simplicity, we can install EMQx with Docker using this Image - Deploy with Docker-compose or CLI:

1
2
docker pull emqx/emqx:5.5.0
docker run -d --name emqx -p 1883:1883 -p 8083:8083 -p 8084:8084 -p 8883:8883 -p 18083:18083 emqx/emqx:5.0.0 #5.5.0

You have other MQTT Broker options like Eclipse Mosquitto, VerneMQ or RabbitMQ

Mosquitto supports many CPU architectures out of the box.

If you have a Raspberry 32bits like me, you can use this Mosquitto Image instead, as the MQTT Broker

1
2
3
4
5
6
7
docker run -d -e TZ=Europe/Madrid -p 1883:1883 mbixtech/arm32v7-mosquitto --name mosquitto
#https://hub.docker.com/r/panuwitp/mosquitto-arm
#https://github.com/somsakc/docker-mosquitto

#docker ps --format ''
  #docker logs mosquitto
  #docker exec -it mosquitto /bin/sh

How to Test EMQx

We can now test that both MQTT Client and Server are ready for our projects.

  • One way to do this is to build some sample script that pushes data:

Sending MQTT Message with Python

We just need Python and Paho installed:

1
pip install paho-mqtt

Create this Python script:

1
2
3
4
5
6
7
8
9
10
11
12
13
import paho.mqtt.publish as publish

# MQTT Broker (EMQX) details
broker_address = "broker.emqx.io" #change to any other adress, like 192.168.3.200 at Home
port = 1883
topic = "python/mqtt"

# Message to publish
message = "Hello from Python!"

# Publish the message
publish.single(topic, message, hostname=broker_address, port=port)
print(f"Message Published to {topic}")

Then just execute it:

1
python3 python-push.py

Sending MQTT Message with C

We will need C installed and the MQTTClient package - which we will build from source:

1
2
3
4
5
6
7
8
9
10
11
sudo apt-get update
sudo apt-get install build-essential git cmake

git clone https://github.com/eclipse/paho.mqtt.c.git
cd paho.mqtt.c

cmake -Bbuild -H. -DPAHO_WITH_SSL=OFF
cd build
make
sudo make install

Create this C script:

1
nano mqtt_publish_server.c

Then we can compile our code

1
2
gcc -o mqtt_publish_server mqtt_publish_server.c -lpaho-mqtt3c #compile
./mqtt_publish_server #execute

How to Visualize MQTT Data

Node-Red

Install Node-Red with Docker - we will use this image:

1
docker run -it -p 1880:1880 -v myNodeREDdata:/data --name mynodered nodered/node-red

You can access Node-Red now at: localhost:1880

Then in the UI: go tu user settings -> Install and add both (node-red-contrib-open and node-red-dashboard)

You can use [this docker-compose] to deploy Node-Red together with EMQx

MQTT-Explorer

With MQTT-Explorer we can have a quick look on the trends of data we are receiving.

It is cross platform and you can install it with:

1
snap install mqtt-explorer #app-image also available

PostMan

You can subscribe to MQTT Topics with Postman, plus you will have a nice real time visualization out of the box.

Install it with:

1
flatpak install flathub com.getpostman.Postman

Added this thanks to nopnop2002 Project

MQTT with Home Assistant

We can install HA with Docker to have it ready for our MQTT projects


FAQ

How to Install HA

You can install Home Assistant with Docker following this steps.

It is part of another IoT Project with InfluxDB and DHT11.

  • Go to: localhost:8123

Then use the MQTT Integration (we are lucky it is not an add-on)

  • Settings - Devices and Services -> Add Integration -> MQTT
    • Then you will add the address and port of your MQTT Broker (and user/pass if needed)

To finish, configure MQTT integration listen to the topic that you are interested to get data.

https://github.com/home-assistant/core/tree/dev/homeassistant/components/mqtt

How to Deploy EMQx with Docker

How to build EMQx for ARM32

https://github.com/emqx/emqx?tab=readme-ov-file#build-from-source https://github.com/erlang/otp

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
wget https://packages.erlang-solutions.com/erlang-solutions_2.0_all.deb
sudo dpkg -i erlang-solutions_2.0_all.deb
sudo apt-get update


# sudo apt update

# git clone https://github.com/erlang/otp.git
# cd otp

# git checkout maint-25    # current latest stable version
# ./configure
# make
# make install

#sudo apt install erlang

docker run erlang:25
erl -version
1
2
3
4
git clone https://github.com/emqx/emqx.git
cd emqx
make
_build/emqx/rel/emqx/bin/emqx console

How to visualize MQTT Data

  • With Grafana - https://grafana.com/grafana/plugins/grafana-mqtt-datasource/
  • With Postman
  • With ekuiper
1
docker run -p 9081:9081 -d --name ekuiper -e MQTT_SOURCE__DEFAULT__SERVER=tcp://broker.emqx.io:1883 lfedge/ekuiper:latest

PostMan Alternatives

How to Push Data to MQTT

  • With Python - https://www.emqx.com/en/blog/how-to-use-mqtt-in-python
  • With Micro Python - https://www.youtube.com/watch?v=THUGLRGuOU8
  • With C
  • With Rust - https://www.emqx.com/en/blog/how-to-use-mqtt-in-rust
  • MQTT Client ESP 32 + RPi - https://www.youtube.com/watch?v=ebsXSCKsHeQ

How about Streaming?

https://www.emqx.com/en/blog/connecting-millions-of-cars-using-emqx-mqtt-and-upstash-kafka https://upstash.com/docs/oss/sdks/ts/kafka/overview

When talking about streaming, think about Kafka.

Content that was helpful to put this together

  • Push MQTT Data to Node-Red Gauge https://www.youtube.com/watch?v=c3WYSUaFZqA
  • Setup Dashboard tools on Node-Red: https://www.youtube.com/watch?v=TNHAZxwB-9o

IoV - Internet of Vehicles

What about CanBus?

CAN bus is like a private walkie-talkie system used by different parts of a car to talk to each other quickly and directly, helping them work together smoothly.

But MQTT is more like sending messages through a mail system, where you write a message, put it in an envelope with an address (called a topic), and send it to a central post office (called a broker), which then delivers the message to anyone who is interested in receiving it.

While CAN bus is great for fast and direct communication within a single place, like a car, MQTT is better for sending messages between different places or devices, like smart home gadgets, over the internet.

This might be helpful ~ CANBUS * CAN what? https://www.youtube.com/watch?v=JZSCzRT9TTo * https://www.emqx.com/en/blog/bridging-demanded-signals-from-can-bus-to-mqtt-by-ekuiper * https://github.com/linux-can/can-utils * Can to MQTT: https://github.com/nopnop2002/esp-idf-can2mqtt * ESP32 - CAN: https://www.youtube.com/watch?v=Se2KCVyD7CM * https://github.com/nopnop2002/esp-idf-mqtt-client * https://github.com/nopnop2002/esp-idf-can2websocket * https://github.com/nopnop2002/esp-idf-CANBus-Monitor * https://github.com/c3re/can2mqtt ```sh # sudo apt-get install can-utils # ifconfig -a # sudo ip link set can0 up type can bitrate 500000 #Replace can0 with the appropriate interface name and 500000 with the desired bitrate if necessary. ```
This post is licensed under CC BY 4.0 by the author.