ESP-NOW with ESP32: Receive Data from Multiple Boards (many-to-one)
Learn how to setup an ESP32 board to receive data from multiple ESP32 boards via ESP-NOW communication protocol (many-to-one configuration) with Arduino IDE.
- Suitable forB.Tech/Diploma IoT/ESP32 students
- Build time1-2 weeks
- LevelIntermediate
- Available atAjvika Labs, Kakinada
About this project
This tutorial shows how to set up an ESP32 board to receive data from multiple ESP32 boards via ESP-NOW communication protocol (many-to-one configuration). This configuration is ideal if you want to collect data from several sensors nodes into one ESP32 board. The boards will be programmed using Arduino IDE.
We have other guides related with ESP-NOW that you might be interested in:
Getting Started with ESP-NOW (ESP32 with Arduino IDE)
ESP-NOW Two-Way Communication Between ESP32 Boards
ESP-NOW with ESP32: Send Data to Multiple Boards (one-to-many)
Project Overview
This tutorial shows how to setup an ESP32 board to receive data from multiple ESP32 boards via ESP-NOW communication protocol (many-to-one configuration) as shown in the following figure.
One ESP32 board acts as a receiver/slave;
Multiple ESP32 boards act as senders/masters. We’ve tested this example with 5 ESP32 sender boards and it worked fine. You should be able to add more boards to your setup;
The sender board receives an acknowledge message indicating if the message was successfully delivered or not;
The ESP32 receiver board receives the messages from all senders and identifies which board sent the message;
As an example, we’ll exchange random values between the boards. You should modify this example to send commands or sensor readings (
exchange sensor readings using ESP-NOW
).
Note:
in the ESP-NOW documentation there isn’t such thing as “sender/master” and “receiver/slave”. Every board can be a sender or receiver. However, to keep things clear we’ll use the terms “sender” and “receiver” or “master” and “slave”.
Prerequisites
We’ll program the ESP32 boards using Arduino IDE, so before proceeding with this tutorial, make sure you have these boards installed in your Arduino IDE.
Installing ESP32 Board in Arduino IDE (Windows, Mac OS X, and Linux)
Parts Required
To follow this tutorial, you need multiple ESP32 boards. All ESP32 models should work. We’ve experimented with different models of ESP32 boards and all worked well (
ESP32 DOIT board
TTGO T-Journal
ESP32 with OLED board
and
ESP32-CAM
).
ESP32
(read
Best ESP32 development boards
)
You can use the preceding links or go directly to
MakerAdvisor.com/tools
to find all the parts for your projects at the best price!
Getting the Receiver Board MAC Address
To send messages via ESP-NOW, you need to know the receiver board’s
MAC address
. Each board has a unique MAC address (learn how to
Get and Change the ESP32 MAC Address
).
Upload the following code to your ESP32 receiver board to get is MAC address.
/*
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files.
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
*/
#ifdef ESP32
#include <WiFi.h>
#include <esp_wifi.h>
#else
#include <ESP8266WiFi.h>
#endif
void setup(){
Serial.begin(115200);
Serial.print("ESP Board MAC Address: ");
#ifdef ESP32
WiFi.mode(WIFI_STA);
WiFi.STA.begin();
uint8_t baseMac[6];
esp_err_t ret = esp_wifi_get_mac(WIFI_IF_STA, baseMac);
if (ret == ESP_OK) {
Serial.printf("%02x:%02x:%02x:%02x:%02x:%02x\n",
baseMac[0], baseMac[1], baseMac[2],
baseMac[3], baseMac[4], baseMac[5]);
} else {
Serial.println("Failed to read MAC address");
}
#else
Serial.println(WiFi.macAddress());
#endif
}
void loop(){
}
After uploading the code, press the RST/EN button, and the MAC address should be displayed on the Serial Monitor.
ESP32 Sender Code (ESP-NOW)
The receiver can identify each sender by its unique MAC address. However, dealing with different MAC addresses on the Receiver side to identify which board sent which message can be tricky.
So, to make things easier, we’ll identify each board with a unique number (
id
) that starts at 1. If you have three boards, one will have ID number 1, the other number 2, and finally number 3. The ID will be sent to the receiver alongside the other variables.
As an example, we’ll exchange a structure that contains the board
id
number and two random numbers
and
y
as shown in the figure below.
Upload the following code to each of your sender boards. Don’t forget to increment the
id
number for each sender board.
/*********
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files.
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
*********/
#include <esp_now.h>
#include <WiFi.h>
// REPLACE WITH THE RECEIVER'S MAC Address
uint8_t broadcastAddress[] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
// Structure example to send data
// Must match the receiver structure
typedef struct struct_message {
int id; // must be unique for each sender board
int x;
int y;
} struct_message;
// Create a struct_message called myData
struct_message myData;
// Create peer interface
esp_now_peer_info_t peerInfo;
// callback when data is sent
void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status) {
Serial.print("\r\nLast Packet Send Status:\t");
Serial.println(status == ESP_NOW_SEND_SUCCESS ? "Delivery Success" : "Delivery Fail");
}
void setup() {
// Init Serial Monitor
Serial.begin(115200);
// Set device as a Wi-Fi Station
WiFi.mode(WIFI_STA);
// Init ESP-NOW
if (esp_now_init() != ESP_OK) {
Serial.println("Error initializing ESP-NOW");
return;
}
// Once ESPNow is successfully Init, we will register for Send CB to
// get the status of Trasnmitted packet
esp_now_register_send_cb(esp_now_send_cb_t(OnDataSent));
// Register peer
memcpy(peerInfo.peer_addr, broadcastAddress, 6);
peerInfo.channel = 0;
peerInfo.encrypt = false;
// Add peer
if (esp_now_add_peer(&peerInfo) != ESP_OK){
Serial.println("Failed to add peer");
return;
}
}
void loop() {
// Set values to send
myData.id = 1;
myData.x = random(0,50);
myData.y = random(0,50);
// Send message via ESP-NOW
esp_err_t result = esp_now_send(broadcastAddress, (uint8_t *) &myData, sizeof(myData));
if (result == ESP_OK) {
Serial.println("Sent with success");
}
else {
Serial.println("Error sending the data");
}
delay(10000);
}
How the Code Works
Include the
WiFi
and
esp_now
libraries.
#include <esp_now.h>
#include <WiFi.h>
Insert the receiver’s MAC address on the following line.
uint8_t broadcastAddress[] = {0x30, 0xAE, 0xA4, 0x15, 0xC7, 0xFC};
Then, create a structure that contains the data we want to send. We called this structure
struct_message
and it contains three integer variables: the board
id
and
y
. You can change this to send whatever variable types you want (but don’t forget to change that on the receiver side too).
typedef struct struct_message {
int id; // must be unique for each sender board
int x;
int y;
} struct_message;
Create a new variable of type
struct_message
that is called
myData
that will store the variables’ values.
struct_message myData;
Create a variable of type
esp_now_peer_info_t
to store information about the peer.
esp_now_peer_info_t peerInfo;
OnDataSent() callback function
Next, define the
OnDataSent()
function. This is a callback function that will be executed when a message is sent. In this case, this function prints if the message was successfully delivered or not.
void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status) {
Serial.print("\r\nLast P
We have other guides related with ESP-NOW that you might be interested in:
Getting Started with ESP-NOW (ESP32 with Arduino IDE)
ESP-NOW Two-Way Communication Between ESP32 Boards
ESP-NOW with ESP32: Send Data to Multiple Boards (one-to-many)
Project Overview
This tutorial shows how to setup an ESP32 board to receive data from multiple ESP32 boards via ESP-NOW communication protocol (many-to-one configuration) as shown in the following figure.
One ESP32 board acts as a receiver/slave;
Multiple ESP32 boards act as senders/masters. We’ve tested this example with 5 ESP32 sender boards and it worked fine. You should be able to add more boards to your setup;
The sender board receives an acknowledge message indicating if the message was successfully delivered or not;
The ESP32 receiver board receives the messages from all senders and identifies which board sent the message;
As an example, we’ll exchange random values between the boards. You should modify this example to send commands or sensor readings (
exchange sensor readings using ESP-NOW
).
Note:
in the ESP-NOW documentation there isn’t such thing as “sender/master” and “receiver/slave”. Every board can be a sender or receiver. However, to keep things clear we’ll use the terms “sender” and “receiver” or “master” and “slave”.
Prerequisites
We’ll program the ESP32 boards using Arduino IDE, so before proceeding with this tutorial, make sure you have these boards installed in your Arduino IDE.
Installing ESP32 Board in Arduino IDE (Windows, Mac OS X, and Linux)
Parts Required
To follow this tutorial, you need multiple ESP32 boards. All ESP32 models should work. We’ve experimented with different models of ESP32 boards and all worked well (
ESP32 DOIT board
TTGO T-Journal
ESP32 with OLED board
and
ESP32-CAM
).
ESP32
(read
Best ESP32 development boards
)
You can use the preceding links or go directly to
MakerAdvisor.com/tools
to find all the parts for your projects at the best price!
Getting the Receiver Board MAC Address
To send messages via ESP-NOW, you need to know the receiver board’s
MAC address
. Each board has a unique MAC address (learn how to
Get and Change the ESP32 MAC Address
).
Upload the following code to your ESP32 receiver board to get is MAC address.
/*
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files.
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
*/
#ifdef ESP32
#include <WiFi.h>
#include <esp_wifi.h>
#else
#include <ESP8266WiFi.h>
#endif
void setup(){
Serial.begin(115200);
Serial.print("ESP Board MAC Address: ");
#ifdef ESP32
WiFi.mode(WIFI_STA);
WiFi.STA.begin();
uint8_t baseMac[6];
esp_err_t ret = esp_wifi_get_mac(WIFI_IF_STA, baseMac);
if (ret == ESP_OK) {
Serial.printf("%02x:%02x:%02x:%02x:%02x:%02x\n",
baseMac[0], baseMac[1], baseMac[2],
baseMac[3], baseMac[4], baseMac[5]);
} else {
Serial.println("Failed to read MAC address");
}
#else
Serial.println(WiFi.macAddress());
#endif
}
void loop(){
}
After uploading the code, press the RST/EN button, and the MAC address should be displayed on the Serial Monitor.
ESP32 Sender Code (ESP-NOW)
The receiver can identify each sender by its unique MAC address. However, dealing with different MAC addresses on the Receiver side to identify which board sent which message can be tricky.
So, to make things easier, we’ll identify each board with a unique number (
id
) that starts at 1. If you have three boards, one will have ID number 1, the other number 2, and finally number 3. The ID will be sent to the receiver alongside the other variables.
As an example, we’ll exchange a structure that contains the board
id
number and two random numbers
and
y
as shown in the figure below.
Upload the following code to each of your sender boards. Don’t forget to increment the
id
number for each sender board.
/*********
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files.
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
*********/
#include <esp_now.h>
#include <WiFi.h>
// REPLACE WITH THE RECEIVER'S MAC Address
uint8_t broadcastAddress[] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF};
// Structure example to send data
// Must match the receiver structure
typedef struct struct_message {
int id; // must be unique for each sender board
int x;
int y;
} struct_message;
// Create a struct_message called myData
struct_message myData;
// Create peer interface
esp_now_peer_info_t peerInfo;
// callback when data is sent
void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status) {
Serial.print("\r\nLast Packet Send Status:\t");
Serial.println(status == ESP_NOW_SEND_SUCCESS ? "Delivery Success" : "Delivery Fail");
}
void setup() {
// Init Serial Monitor
Serial.begin(115200);
// Set device as a Wi-Fi Station
WiFi.mode(WIFI_STA);
// Init ESP-NOW
if (esp_now_init() != ESP_OK) {
Serial.println("Error initializing ESP-NOW");
return;
}
// Once ESPNow is successfully Init, we will register for Send CB to
// get the status of Trasnmitted packet
esp_now_register_send_cb(esp_now_send_cb_t(OnDataSent));
// Register peer
memcpy(peerInfo.peer_addr, broadcastAddress, 6);
peerInfo.channel = 0;
peerInfo.encrypt = false;
// Add peer
if (esp_now_add_peer(&peerInfo) != ESP_OK){
Serial.println("Failed to add peer");
return;
}
}
void loop() {
// Set values to send
myData.id = 1;
myData.x = random(0,50);
myData.y = random(0,50);
// Send message via ESP-NOW
esp_err_t result = esp_now_send(broadcastAddress, (uint8_t *) &myData, sizeof(myData));
if (result == ESP_OK) {
Serial.println("Sent with success");
}
else {
Serial.println("Error sending the data");
}
delay(10000);
}
How the Code Works
Include the
WiFi
and
esp_now
libraries.
#include <esp_now.h>
#include <WiFi.h>
Insert the receiver’s MAC address on the following line.
uint8_t broadcastAddress[] = {0x30, 0xAE, 0xA4, 0x15, 0xC7, 0xFC};
Then, create a structure that contains the data we want to send. We called this structure
struct_message
and it contains three integer variables: the board
id
and
y
. You can change this to send whatever variable types you want (but don’t forget to change that on the receiver side too).
typedef struct struct_message {
int id; // must be unique for each sender board
int x;
int y;
} struct_message;
Create a new variable of type
struct_message
that is called
myData
that will store the variables’ values.
struct_message myData;
Create a variable of type
esp_now_peer_info_t
to store information about the peer.
esp_now_peer_info_t peerInfo;
OnDataSent() callback function
Next, define the
OnDataSent()
function. This is a callback function that will be executed when a message is sent. In this case, this function prints if the message was successfully delivered or not.
void OnDataSent(const uint8_t *mac_addr, esp_now_send_status_t status) {
Serial.print("\r\nLast P
Technologies used
Hardware components
- ESP32
- ESP32-CAM
- ESP8266
- Arduino
- OLED
Software & tools
- Arduino IDE
What you get
- Working project / hardware kit, tested before delivery
- Complete source code with explanation
- Project demo and guidance for your viva
- Project report, PPT and IEEE paper support (on request)
Delivery & Payment
Delivery takes a minimum of two weeks from the date your inquiry is confirmed.
Payment is in two parts:
• 50% advance to start the project
• Remaining 50% before delivery
Note:
• Documentation and PPT are not included by default
• If you need documentation/PPT, it can be arranged for extra time and cost
We'll confirm the exact timeline and cost with you after reviewing your requirements.