Communication Wi-Fi client-serveur ESP32 entre deux cartes

Communication Wi-Fi client-serveur ESP32 entre deux cartes

Ce guide montre comment configurer une communication HTTP entre deux cartes ESP32 pour échanger des données via Wi-Fi sans connexion Internet (routeur). En termes simples, vous apprendrez à envoyer des données d’une carte à l’autre à l’aide de requêtes HTTP. Les cartes ESP32 seront programmées à l’aide de l’IDE Arduino.

Communication Wi-Fi client-serveur ESP32 entre deux cartes

À des fins de démonstration, nous enverrons les relevés des capteurs BME280 d’une carte à l’autre. Le récepteur affichera les lectures sur un écran OLED.

Si vous avez une carte ESP8266, vous pouvez lire ce guide dédié : ESP8266 NodeMCU Client-Server Wi-Fi Communication.

Regardez la démonstration vidéo

Pour voir comment fonctionne le projet, vous pouvez regarder la vidéo de démonstration suivante :

Aperçu du projet

Une carte ESP32 agira en tant que serveur et l’autre carte ESP32 agira en tant que client. Le diagramme suivant montre un aperçu de la façon dont tout fonctionne.

Aperçu de la communication Wi-Fi client-serveur ESP32 entre le projet
  • Le serveur ESP32 crée son propre réseau sans fil (ESP32 Soft-Access Point). Ainsi, d’autres appareils Wi-Fi peuvent se connecter à ce réseau (SSID : Point d’accès ESP32, Mot de passe: 123456789).
  • Le client ESP32 est défini comme une station. Ainsi, il peut se connecter au réseau sans fil du serveur ESP32.
  • Le client peut envoyer des requêtes HTTP GET au serveur pour demander des données de capteur ou toute autre information. Il lui suffit d’utiliser l’adresse IP du serveur pour faire une requête sur une certaine route : /Température, /humidité ou /pression.
  • Le serveur écoute les demandes entrantes et envoie une réponse appropriée avec les lectures.
  • Le client reçoit les lectures et les affiche sur l’écran OLED.

A titre d’exemple, le client ESP32 demande la température, l’humidité et la pression au serveur en faisant des requêtes sur l’adresse IP du serveur suivie de /Température, /humidité et /pressionrespectivement.

Le serveur ESP32 écoute sur ces routes et lorsqu’une demande est faite, il envoie les lectures de capteur correspondantes via une réponse HTTP.

Pièces requises

Pièces requises pour la communication client-serveur ESP32

Pour ce tutoriel, vous avez besoin des pièces suivantes :

Vous pouvez utiliser les liens précédents ou accéder directement à MakerAdvisor.com/tools pour trouver toutes les pièces pour vos projets au meilleur prix !

Communication Wi Fi client serveur ESP32 entre deux cartes

Installation des bibliothèques

Pour ce tutoriel, vous devez installer les bibliothèques suivantes :

Bibliothèques de serveurs Web asynchrones

Nous utiliserons les bibliothèques suivantes pour gérer la requête HTTP :

Ces bibliothèques ne peuvent pas être installées via le gestionnaire de bibliothèques. Vous devez donc décompresser les bibliothèques et les déplacer dans le dossier des bibliothèques d’installation de l’IDE Arduino.

Alternativement, vous pouvez aller à Esquisser > Inclure la bibliothèque > Ajouter une bibliothèque .ZIP… et sélectionnez les bibliothèques que vous venez de télécharger.

Vous pourriez également aimer : Construire un serveur Web asynchrone avec l’ESP32

Bibliothèques BME280

Les bibliothèques suivantes peuvent être installées via le gestionnaire de bibliothèque Arduino. Aller à Esquisser > Inclure la bibliothèque> Gérer les bibliothèques et recherchez le nom de la bibliothèque.

Vous aimerez aussi : Interface BME280 avec ESP32 (Guide)

Bibliothèques I2C SSD1306 OLED

Pour interfacer avec l’écran OLED, vous avez besoin des bibliothèques suivantes. Ceux-ci peuvent être installés via le gestionnaire de bibliothèque Arduino. Aller à Esquisser > Inclure la bibliothèque> Gérer les bibliothèques et recherchez le nom de la bibliothèque.

Vous pourriez également aimer : Écran I2C SSD1306 OLED avec ESP32 (Guide)

#1 Serveur ESP32 (point d’accès)

Serveur ESP32 avec BME280 température humidité pression

Le serveur ESP32 est un point d’accès (AP), qui écoute les requêtes sur le /Température, /humidité et /pression URL. Lorsqu’il reçoit des requêtes sur ces URL, il envoie les dernières lectures du capteur BME280.

À des fins de démonstration, nous utilisons un capteur BME280, mais vous pouvez utiliser n’importe quel autre capteur en modifiant quelques lignes de code.

Diagramme schématique

Câblez l’ESP32 au capteur BME280 comme indiqué dans le schéma suivant.

Schéma de câblage ESP32 BME280
BME280 ESP32
NIV/VCC 3.3V
Terre Terre
SCL GPIO 22
SDA GPIO 21

Esquisse Arduino pour le serveur ESP32 #1

Téléchargez le code suivant sur votre tableau.

/*
  Rui Santos
  Complete project details at https://Raspberryme.com/esp32-client-server-wi-fi/
  
  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.
*/

// Import required libraries
#include "WiFi.h"
#include "ESPAsyncWebServer.h"

#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BME280.h>

// Set your access point network credentials
const char* ssid = "ESP32-Access-Point";
const char* password = "123456789";

/*#include <SPI.h>
#define BME_SCK 18
#define BME_MISO 19
#define BME_MOSI 23
#define BME_CS 5*/

Adafruit_BME280 bme; // I2C
//Adafruit_BME280 bme(BME_CS); // hardware SPI
//Adafruit_BME280 bme(BME_CS, BME_MOSI, BME_MISO, BME_SCK); // software SPI

// Create AsyncWebServer object on port 80
AsyncWebServer server(80);

String readTemp() {
  return String(bme.readTemperature());
  //return String(1.8 * bme.readTemperature() + 32);
}

String readHumi() {
  return String(bme.readHumidity());
}

String readPres() {
  return String(bme.readPressure() / 100.0F);
}

void setup(){
  // Serial port for debugging purposes
  Serial.begin(115200);
  Serial.println();
  
  // Setting the ESP as an access point
  Serial.print("Setting AP (Access Point)…");
  // Remove the password parameter, if you want the AP (Access Point) to be open
  WiFi.softAP(ssid, password);

  IPAddress IP = WiFi.softAPIP();
  Serial.print("AP IP address: ");
  Serial.println(IP);

  server.on("/temperature", HTTP_GET, [](AsyncWebServerRequest *request){
    request->send_P(200, "text/plain", readTemp().c_str());
  });
  server.on("/humidity", HTTP_GET, [](AsyncWebServerRequest *request){
    request->send_P(200, "text/plain", readHumi().c_str());
  });
  server.on("/pressure", HTTP_GET, [](AsyncWebServerRequest *request){
    request->send_P(200, "text/plain", readPres().c_str());
  });
  
  bool status;

  // default settings
  // (you can also pass in a Wire library object like &Wire2)
  status = bme.begin(0x76);  
  if (!status) {
    Serial.println("Could not find a valid BME280 sensor, check wiring!");
    while (1);
  }
  
  // Start server
  server.begin();
}
 
void loop(){
  
}

Afficher le code brut

Comment fonctionne le code

Commencez par inclure les bibliothèques nécessaires. Inclure le WiFi.h bibliothèque et la ESPAsyncWebServer.h bibliothèque pour gérer les requêtes HTTP entrantes.

#include "WiFi.h"
#include "ESPAsyncWebServer.h"

Incluez les bibliothèques suivantes pour l’interface avec le capteur BME280.

#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BME280.h>

Dans les variables suivantes, définissez les identifiants réseau de votre point d’accès :

const char* ssid = "ESP32-Access-Point";
const char* password = "123456789";

Nous configurons le SSID sur Point d’accès ESP32, mais vous pouvez lui donner n’importe quel autre nom. Vous pouvez également modifier le mot de passe. Par défaut, il est réglé sur 123456789.

Créez une instance pour le capteur BME280 appelée bme.

Adafruit_BME280 bme;

Créez un serveur Web asynchrone sur le port 80.

AsyncWebServer server(80);

Ensuite, créez trois fonctions qui renvoient la température, l’humidité et la pression sous forme de variables String.

String readTemp() {
  return String(bme.readTemperature());
  //return String(1.8 * bme.readTemperature() + 32);
}

String readHumi() {
  return String(bme.readHumidity());
}

String readPres() {
  return String(bme.readPressure() / 100.0F);
}

Dans le mettre en place()initialisez le moniteur série à des fins de démonstration.

Serial.begin(115200);

Définissez votre ESP32 comme point d’accès avec le nom SSID et le mot de passe définis précédemment.

WiFi.softAP(ssid, password);

Ensuite, gérez les routes où l’ESP32 écoutera les requêtes entrantes.

Par exemple, lorsque le serveur ESP32 reçoit une requête sur le /Température URL, il envoie la température retournée par le readTemp() fonctionner comme un caractère (c’est pourquoi nous utilisons le c_str() méthode.

server.on("/temperature", HTTP_GET, [](AsyncWebServerRequest *request){
  request->send_P(200, "text/plain", readTemp().c_str());
});

La même chose se produit lorsque l’ESP reçoit une demande sur le /humidité et /pression URL.

server.on("/humidity", HTTP_GET, [](AsyncWebServerRequest *request){
  request->send_P(200, "text/plain", readHumi().c_str());
});
server.on("/pressure", HTTP_GET, [](AsyncWebServerRequest *request){
  request->send_P(200, "text/plain", readPres().c_str());
});

Les lignes suivantes initialisent le capteur BME280.

bool status;

// default settings
// (you can also pass in a Wire library object like &Wire2)
status = bme.begin(0x76);
if (!status) {
  Serial.println("Could not find a valid BME280 sensor, check wiring!");
  while (1);
}

Enfin, démarrez le serveur.

server.begin();

Comme il s’agit d’un serveur Web asynchrone, il n’y a rien dans le boucler().

void loop(){

}

Test du serveur ESP32

Téléchargez le code sur votre carte et ouvrez le moniteur série. Vous devriez obtenir quelque chose comme suit :

Test de l'ESP32 Server Serial Monitor Arduino IDE

Cela signifie que le point d’accès a été défini avec succès.

Maintenant, pour vous assurer qu’il écoute les demandes de température, d’humidité et de pression, vous devez vous connecter à son réseau.

Dans votre smartphone, rendez-vous dans les paramètres Wi-Fi et connectez-vous au Point d’accès ESP32. Le mot de passe est 123456789.

Connexion point d'accès serveur ESP32

Une fois connecté au point d’accès, ouvrez votre navigateur et tapez 192.168.4.1/température

Vous devriez obtenir la valeur de température dans votre navigateur :

Température de demande de test AP du point d'accès du serveur ESP32

Essayez ce chemin d’URL pour l’humidité 192.168.4.1/humidité:

ESP32 Server Access Point AP Demande de test d'humidité

Enfin, rendez-vous sur 192.168.4.1/pression URL :

Pression de demande de test AP du point d'accès du serveur ESP32

Si vous obtenez des lectures valides, cela signifie que tout fonctionne correctement. Maintenant, vous devez préparer l’autre carte ESP32 (client) pour faire ces demandes pour vous et les afficher sur l’écran OLED.

#2 Client ESP32 (Station)

Le client ESP32 reçoit des lectures via HTTP GET Request BME280

Le client ESP32 est une station Wi-Fi connectée au serveur ESP32. Le client demande la température, l’humidité et la pression au serveur en effectuant des requêtes HTTP GET sur le /Température, /humiditéet /pression Routes d’URL. Ensuite, il affiche les lectures sur un écran OLED.

Diagramme schématique

Câblez l’ESP32 à l’écran OLED comme indiqué dans le schéma suivant.

1644837130 952 Communication Wi Fi client serveur ESP32 entre deux cartes
OLED ESP32
NIV/VCC NIV
Terre Terre
SCL GPIO 22
SDA GPIO 21

Esquisse Arduino pour le client #2 ESP32

Téléchargez le code suivant sur l’autre ESP32 :

/*
  Rui Santos
  Complete project details at https://Raspberryme.com/esp32-client-server-wi-fi/
  
  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 <WiFi.h>
#include <HTTPClient.h>

const char* ssid = "ESP32-Access-Point";
const char* password = "123456789";

//Your IP address or domain name with URL path
const char* serverNameTemp = "http://192.168.4.1/temperature";
const char* serverNameHumi = "http://192.168.4.1/humidity";
const char* serverNamePres = "http://192.168.4.1/pressure";

#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define SCREEN_WIDTH 128 // OLED display width, in pixels
#define SCREEN_HEIGHT 64 // OLED display height, in pixels

// Declaration for an SSD1306 display connected to I2C (SDA, SCL pins)
#define OLED_RESET     4 // Reset pin # (or -1 if sharing Arduino reset pin)
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);

String temperature;
String humidity;
String pressure;

unsigned long previousMillis = 0;
const long interval = 5000; 

void setup() {
  Serial.begin(115200);
  
  // Address 0x3C for 128x64, you might need to change this value (use an I2C scanner)
  if(!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) {
    Serial.println(F("SSD1306 allocation failed"));
    for(;;); // Don't proceed, loop forever
  }
  display.clearDisplay();
  display.setTextColor(WHITE);
  
  WiFi.begin(ssid, password);
  Serial.println("Connecting");
  while(WiFi.status() != WL_CONNECTED) { 
    delay(500);
    Serial.print(".");
  }
  Serial.println("");
  Serial.print("Connected to WiFi network with IP Address: ");
  Serial.println(WiFi.localIP());
}

void loop() {
  unsigned long currentMillis = millis();
  
  if(currentMillis - previousMillis >= interval) {
     // Check WiFi connection status
    if(WiFi.status()== WL_CONNECTED ){ 
      temperature = httpGETRequest(serverNameTemp);
      humidity = httpGETRequest(serverNameHumi);
      pressure = httpGETRequest(serverNamePres);
      Serial.println("Temperature: " + temperature + " *C - Humidity: " + humidity + " % - Pressure: " + pressure + " hPa");
      
      display.clearDisplay();
      
      // display temperature
      display.setTextSize(2);
      display.setTextColor(WHITE);
      display.setCursor(0,0);
      display.print("T: ");
      display.print(temperature);
      display.print(" ");
      display.setTextSize(1);
      display.cp437(true);
      display.write(248);
      display.setTextSize(2);
      display.print("C");
      
      // display humidity
      display.setTextSize(2);
      display.setCursor(0, 25);
      display.print("H: ");
      display.print(humidity);
      display.print(" %"); 
      
      // display pressure
      display.setTextSize(2);
      display.setCursor(0, 50);
      display.print("P:");
      display.print(pressure);
      display.setTextSize(1);
      display.setCursor(110, 56);
      display.print("hPa");
           
      display.display();
      
      // save the last HTTP GET Request
      previousMillis = currentMillis;
    }
    else {
      Serial.println("WiFi Disconnected");
    }
  }
}

String httpGETRequest(const char* serverName) {
  WiFiClient client;
  HTTPClient http;
    
  // Your Domain name with URL path or IP address with path
  http.begin(client, serverName);
  
  // Send HTTP POST request
  int httpResponseCode = http.GET();
  
  String payload = "--"; 
  
  if (httpResponseCode>0) {
    Serial.print("HTTP Response code: ");
    Serial.println(httpResponseCode);
    payload = http.getString();
  }
  else {
    Serial.print("Error code: ");
    Serial.println(httpResponseCode);
  }
  // Free resources
  http.end();

  return payload;
}

Afficher le code brut

Comment fonctionne le code

Incluez les bibliothèques nécessaires pour la connexion Wi-Fi et pour effectuer des requêtes HTTP :

#include <WiFi.h>
#include <HTTPClient.h>

Insérez les informations d’identification du réseau du serveur ESP32. Si vous avez modifié les informations d’identification réseau par défaut sur le serveur ESP32, vous devez les modifier ici pour qu’elles correspondent.

const char* ssid = "ESP32-Access-Point";
const char* password = "123456789";

Ensuite, enregistrez les URL où le client fera des requêtes HTTP. Le serveur ESP32 a l’adresse IP 192.168.4.1, et nous ferons des demandes sur le /Température, /humidité et /pression URL.

const char* serverNameTemp = "http://192.168.4.1/temperature";
const char* serverNameHumi = "http://192.168.4.1/humidity";
const char* serverNamePres = "http://192.168.4.1/pressure";

Inclure les bibliothèques pour s’interfacer avec l’écran OLED :

#include <SPI.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

Définissez la taille de l’affichage OLED :

#define SCREEN_WIDTH 128 // OLED display width, in pixels
#define SCREEN_HEIGHT 64 // OLED display height, in pixels

Créer un affichage objet avec la taille que vous avez définie précédemment et avec le protocole de communication I2C.

Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);

Initialisez les variables de chaîne qui contiendront les relevés de température, d’humidité et de pression récupérés par le serveur.

String temperature;
String humidity;
String pressure;

Définissez l’intervalle de temps entre chaque demande. Par défaut, il est défini sur 5 secondes, mais vous pouvez le modifier sur n’importe quel autre intervalle.

const long interval = 5000; 

Dans le mettre en place()initialisez l’affichage OLED :

// Address 0x3C for 128x64, you might need to change this value (use an I2C scanner)
if(!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) {
  Serial.println(F("SSD1306 allocation failed"));
  for(;;); // Don't proceed, loop forever
}
display.clearDisplay();
display.setTextColor(WHITE);

Noter: si votre écran OLED ne fonctionne pas, vérifiez son adresse I2C à l’aide d’un Croquis du scanner I2C et modifiez le code en conséquence.

Connectez le client ESP32 au réseau du serveur ESP32.

WiFi.begin(ssid, password);
Serial.println("Connecting");
while(WiFi.status() != WL_CONNECTED) { 
  delay(500);
  Serial.print(".");
}
Serial.println("");
Serial.print("Connected to WiFi network with IP Address: ");

Dans le boucler() C’est là que nous faisons les requêtes HTTP GET. Nous avons créé une fonction appelée httpGETRequest() qui accepte comme argument le chemin de l’URL où nous voulons faire la requête et renvoie la réponse sous forme de Chaîne de caractères.

Vous pouvez utiliser la fonction suivante dans vos projets pour simplifier votre code :

String httpGETRequest(const char* serverName) {
  HTTPClient http;
    
  // Your IP address with path or Domain name with URL path 
  http.begin(serverName);
  
  // Send HTTP POST request
  int httpResponseCode = http.GET();
  
  String payload = "--"; 
  
  if (httpResponseCode>0) {
    Serial.print("HTTP Response code: ");
    Serial.println(httpResponseCode);
    payload = http.getString();
  }
  else {
    Serial.print("Error code: ");
    Serial.println(httpResponseCode);
  }
  // Free resources
  http.end();

  return payload;
}

Nous utilisons cette fonction pour obtenir les relevés de température, d’humidité et de pression du serveur.

temperature = httpGETRequest(serverNameTemp);
humidity = httpGETRequest(serverNameHumi);
pressure = httpGETRequest(serverNamePres);

Imprimez ces lectures dans le moniteur série pour le débogage.

Serial.println("Temperature: " + temperature + " *C - Humidity: " + humidity + " % - Pressure: " + pressure + " hPa");

Ensuite, affichez la température sur l’écran OLED :

display.setTextSize(2);
display.setTextColor(WHITE);
display.setCursor(0,0);
display.print("T: ");
display.print(temperature);
display.print(" ");
display.setTextSize(1);
display.cp437(true);
display.write(248);
display.setTextSize(2);
display.print("C");

L’humidité :

display.setTextSize(2);
display.setCursor(0, 25);
display.print("H: ");
display.print(humidity);
display.print(" %"); 

Enfin, la lecture de la pression :

display.setTextSize(2);
display.setCursor(0, 50);
display.print("P:");
display.print(pressure);
display.setTextSize(1);
display.setCursor(110, 56);
display.print("hPa");

display.display();

Nous utilisons des minuteries au lieu de délais pour faire une demande toutes les x nombre de secondes. C’est pourquoi nous avons le précédentMillis, courantMillis variables et utilisez les millis() une fonction. Nous avons un article qui montre la différence entre les minuteries et les retards que vous pourriez trouver utile (ou lisez les minuteurs ESP32).

Téléchargez le croquis sur #2 ESP32 (client) pour tester si tout fonctionne correctement.

Test du client ESP32

Avec les deux cartes assez proches et alimentées, vous verrez que l’ESP #2 reçoit de nouvelles lectures de température, d’humidité et de pression toutes les 5 secondes de l’ESP #1.

C’est ce que vous devriez voir sur le moniteur série du client ESP32.

Test de l'ESP32 Client Serial Monitor Arduino IDE

Les lectures du capteur sont également affichées dans l’OLED.

Exemple d'échange de données ESP32 Client Server Communication pour les réalignements de capteurs

C’est ça! Vos deux tableaux communiquent entre eux.

ESP32 à ESP32 Parler les uns avec les autres avec la communication sans fil

Emballer

Dans ce didacticiel, vous avez appris à envoyer des données d’un ESP32 à un autre ESP32 via Wi-Fi à l’aide de requêtes HTTP sans avoir besoin de vous connecter à Internet. À des fins de démonstration, nous avons montré comment envoyer des lectures de capteur BME280, mais vous pouvez utiliser n’importe quel autre capteur ou envoyer d’autres données. Autres capteurs recommandés :

Nous avons un tutoriel similaire pour l’ESP8266 qui pourrait vous être utile :

Nous espérons que vous avez trouvé ce tutoriel utile. Nous préparons d’autres tutoriels comme ceux-ci. Alors restez connectés et abonnez-vous à notre blog !

Merci d’avoir lu.