Connecting ultrasonic distance sensor to Mainflux

Zivorad Cosovic
Mainflux IoT Platform
6 min readApr 22, 2019


In this tutorial we will demonstrate connecting ultrasonic distance sensor HC-SR04 with Raspberry Pi, and sending data from sensor to locally deployed Mainflux and to cloud deployed Mainflux (Digital Ocean). We will then show that data in Grafana.

We will do following steps:

  • Install paho-mqtt on Raspberry Pi
  • Connect HC-SR04 Ultrasonic Range Sensor on the Raspberry Pi
  • Writing a code for measuring distance and sending data to Mainflux using Python
  • Setting the dashboard Grafana to display data sent to Mainflux
  • Example of sending data from multiple sensors HC-SR04 on Mainflux

We will use:

  • Laptop with Linux OS (Ubuntu 18.04.) with Mainflux installed (create things, channels),
  • Raspberry Pi (Rpi 3 Model B), sensor HC-SR04, wires, protobord for connecting, resistors (R=1kΩ i R=2kΩ) i WiFi internet,
  • On Digital Ocean we have created server account and we have installed Ubuntu 16.04.5 x64, install Docker, Docker Compose and Mainflux (create things, channels).

To follow the next steps it would be useful to first understand steps from this tutorial.

Install paho-mqtt on Raspberry Pi

On Raspberry Pi we have installed operating system Raspbian Strech Lite i and connected it to WiFi.

We need to check the Python version that is installed on Raspbian Strech Lite on RPi command terminal:

$ python3 -V
Python 3.5.3

It is necessary to install paho-mqtt on Raspberry Pi in order to send and publish data on/to Mainflux. For example, to install Python version 3.5 I would need to run:

$ pip3 install paho-mqtt

Connecting HC-SR04 ultrasonic range sensor on the Raspberry Pi

GPIO pins on Raspberry Pi allow us to connect digital sensors directly onto it, but we need to keep in mind all the voltages coming from sensors (ECHO pin HC-SR04), because they are defined with 5V, and GPIO pins RPi tolerate max of 3.3V, so we have to use the voltage divider so the GPIO voltage on pins RPi will be appropriate.


We’ll be using four pins on the Raspberry Pi for this example: GPIO 5V (5V Power), GPIO GND (0V Ground), GPIO 23-TRIG (GPIO Output) and GPIO 24-ECHO (GPIO Input)

Detailed description of sensor HC-SR04 connection with Raspberry Pi could be found here.

sensor HC-SR04 connected on RPi

Writing a code in Python for measuring distance and sending data to Mainflux

In order to access Raspberry Pi from terminal, we use following commands:

$ ssh pi@ip_address
$ password

Now open the file in your favorite editor and write program code. In order to write the Python code, we need to import necessary libraries initialization.

import RPi.GPIO as GPIO
import time
import paho.mqtt.client as mqtt

After which we need to define addresses onto which messages are sent (for example localhost) as well as parameters thing_id, thing_key which are created in Mainflux.

In order to enable sending of messages and connecting in Python, let’s execute following commands

client = mqtt.Client()
client.username_pw_set(thing_id, thing_key)

After that we need to execute initialization of GPIO pins in the code. Those pins will be used for communication between HC-SR04 sensor and RPi (in our example those are the pins GPIO 23 and GPIO 24).

GPIO.setmode(GPIO.BCM)iTriggerPin = 23
iEchoPin = 24
GPIO.setup(iTriggerPin, GPIO.OUT)
GPIO.setup(iEchoPin, GPIO.IN)

In this Python code we measure the distance using the HC-SR04 sensor, using the specifications explained in detail here.

while True:
GPIO.output(iTriggerPin, True)
GPIO.output(iTriggerPin, False)
while GPIO.input(iEchoPin) == 0:
fPulseStart = time.time()
while GPIO.input(iEchoPin) == 1:
fPulseEnd = time.time()
fPulseDuration = fPulseEnd - fPulseStart fDistance = round((fPulseDuration * 171.50), 2) print ("Distance:", fDistance, "m.")

Sending the message on measuring the distance in Mainflux must be in SenML format:


where “n” stands for the name of the parameter that is measured, “u” stands for unit of measure for parameter measured, and “v” is value of parameter measured.

In order to publish this message we use the following Python command

client.publish(topic, payload)

where topic (publish channel), and the payload (message we want to publish) are required parameters that must be defined. For our example, that would look like this:

client.publish(topic = "channels/channel_id/messages", payload = "[{"n":"distance","u":"m","v":"fDistance"}]")

After we have finished writing the code, we should save it onto Raspberry Pi with the filename File_Name.pyand execute it with RPi command:

$ python3

The program we used in this example is here

Setting the dashboard Graphs to display data sent to Mainflux

With Mainflux running we can start additional services of Mainflux platform (those services are InfluxDB database, InfluxDB writer service, and Grafana tool) with command :

$ cd mainflux
$ docker-compose -f docker/addons/influxdb-writer/docker-compose.yml up -d

Navigate to your localhost or server (Digital Ocean) IP address on port 3001. You should see Grafana login page:

Click to add data source and you should see the form for adding new data source.

Choose whatever name you want, we’ll use Mainflux. Next, choose InfluxDB from the drop-down as database type.

Database URL is http://mainflux-influxdb:8086.

If we don’t mention some of the fields, that means those fields are left at its default values. Finally, setup InfluxDB details. Database, user and password all have the same value: mainflux.

After filling these fields, your form should look like this:

InfluxDB data source settings in Grafana

Click save and test. Let’s send some data to Mainflux so we can track them in Grafana.

Create new dashboard in Grafana:

Add new Singlestat

First of all, set data source to be the source you’ve just added (in our case, we named it Mainflux), then adjust the other parameters as shown in the picture

And now we can see Singlestat of distance values we are sending (locally and with server account (Digital Ocean)).

In this tutorial shown how to send data from sensors to Mainflux (localhost and Digital Ocean) and display it on Grafana. Based on this example, we see that we can send data from any sensor to Mainflux. Some of the earlier experiences listed on the links were used to help build this example.

Example of sending data from multiple sensors HC-SR04 on Mainflux

We can connect three sensors to Raspberry Pi and see how it works. To connect, we use other free GPIO pins on Raspberry Pi, taking care about the voltages coming from the sensor (ECHO pin HC-SR04).

3xHC-SR04 sensor connected on RPi

In the program code we have to adjust to work with three sensors, define all the GPIO pins used, program for each sensor should run separately, sending and publishing data from all three sensors. The program we use to run and send data from three sensors is shown here.

By setting Grafana, we add new panel for displaying data from sensors

Grafana display with three sensors looks like this:

Until next time,
Zivorad Cosovic, Milos Ljubisavljevic

About Mainflux company:
Mainflux is a technology company offering a full-stack open-source, patent-free IoT Platform recognized by Linux Foundation and O’Reilly Media with software and hardware consulting services based on extensive working experience in fortune 500 companies.

Mainflux website:
Mainflux Github:



Zivorad Cosovic
Mainflux IoT Platform

Electrical engineer and Mainflux associate