Dans ce didacticiel, vous apprendrez à créer un serveur Web avec l’ESP32 à l’aide du protocole de communication WebSocket. À titre d’exemple, nous allons vous montrer comment créer une page Web pour contrôler les sorties ESP32 à distance. L’état de la sortie est affiché sur la page Web et se met à jour automatiquement dans tous les clients.

L’ESP32 sera programmé à l’aide de l’IDE Arduino et de l’ESPAsyncWebServer. Nous avons également un guide WebSocket similaire pour l’ESP8266.
Si vous avez suivi certains de nos précédents projets de serveur Web comme celui-ci, vous avez peut-être remarqué que si vous avez plusieurs onglets (dans le même ou sur différents appareils) ouverts en même temps, l’état ne se met pas à jour dans tous onglets automatiquement, sauf si vous actualisez la page Web. Pour résoudre ce problème, nous pouvons utiliser le protocole WebSocket – tous les clients peuvent être avertis lorsqu’un changement se produit et mettre à jour la page Web en conséquence.
Ce tutoriel était basé sur un projet créé et documenté par un de nos lecteurs (Stéphane Calderoni). Vous pouvez lire son excellent tutoriel ici.
Présentation de WebSocket
Un WebSocket est une connexion persistante entre un client et un serveur qui permet une communication bidirectionnelle entre les deux parties à l’aide d’une connexion TCP. Cela signifie que vous pouvez envoyer des données du client au serveur et du serveur au client à tout moment.

Le client établit une connexion WebSocket avec le serveur via un processus appelé poignée de main WebSocket. La poignée de main commence par une requête/réponse HTTP, permettant aux serveurs de gérer les connexions HTTP ainsi que les connexions WebSocket sur le même port. Une fois la connexion établie, le client et le serveur peuvent envoyer des données WebSocket en mode full duplex.
Grâce au protocole WebSockets, le serveur (carte ESP32) peut envoyer des informations au client ou à tous les clients sans qu’il soit sollicité. Cela nous permet également d’envoyer des informations au navigateur Web lorsqu’un changement se produit.
Ce changement peut être quelque chose qui s’est produit sur la page Web (vous avez cliqué sur un bouton) ou quelque chose qui s’est produit du côté ESP32, comme appuyer sur un bouton physique sur un circuit.
Aperçu du projet
Voici la page Web que nous allons créer pour ce projet.

- Le serveur Web ESP32 affiche une page Web avec un bouton pour basculer l’état du GPIO 2;
- Pour plus de simplicité, nous contrôlons GPIO 2 – la LED intégrée. Vous pouvez utiliser cet exemple pour contrôler n’importe quel autre GPIO ;
- L’interface affiche l’état GPIO actuel. Chaque fois qu’un changement se produit sur l’état du GPIO, l’interface est mise à jour instantanément ;
- L’état GPIO est mis à jour automatiquement dans tous les clients. Cela signifie que si vous avez plusieurs onglets de navigateur Web ouverts sur le même appareil ou sur différents appareils, ils sont tous mis à jour en même temps.
Comment ça fonctionne?
L’image suivante décrit ce qui se passe lorsque vous cliquez sur le bouton « Basculer ».

Voici ce qui se passe lorsque vous cliquez sur le bouton « Basculer »:
- Cliquez sur le bouton « Basculer » ;
- Le client (votre navigateur) envoie des données via le protocole WebSocket avec le message « toggle » ;
- L’ESP32 (serveur) reçoit ce message, il sait donc qu’il doit basculer l’état de la LED. Si la LED était auparavant éteinte, allumez-la ;
- Ensuite, il envoie des données avec le nouvel état de la LED à tous les clients également via le protocole WebSocket ;
- Les clients reçoivent le message et mettent à jour l’état des voyants sur la page Web en conséquence. Cela nous permet de mettre à jour tous les clients presque instantanément lorsqu’un changement se produit.
Préparation de l’IDE Arduino
Nous programmerons le ESP32 carte à l’aide de l’IDE Arduino, assurez-vous donc de l’avoir installé dans votre IDE Arduino.
Installation de bibliothèques – Serveur Web asynchrone
Pour construire le serveur Web, nous utiliserons le ESPAsyncWebServer bibliothèque. Cette bibliothèque a besoin de AsyncTCP bibliothèque pour fonctionner correctement. Cliquez sur les liens ci-dessous pour télécharger les bibliothèques.
Ces bibliothèques ne peuvent pas être installées via le gestionnaire de bibliothèque Arduino, vous devez donc copier les fichiers de bibliothèque dans le dossier Bibliothèques d’installation Arduino. Alternativement, dans votre IDE Arduino, vous pouvez aller à Sketch> Inclure la bibliothèque> Ajouter une bibliothèque .zip et sélectionner les bibliothèques que vous venez de télécharger.
Code pour le serveur ESP32 WebSocket
Copiez le code suivant dans votre IDE Arduino.
/*********
Rui Santos
Complete project details at https://Raspberryme.com/esp32-websocket-server-arduino/
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 <AsyncTCP.h>
#include <ESPAsyncWebServer.h>
// Replace with your network credentials
const char* ssid = "REPLACE_WITH_YOUR_SSID";
const char* password = "REPLACE_WITH_YOUR_PASSWORD";
bool ledState = 0;
const int ledPin = 2;
// Create AsyncWebServer object on port 80
AsyncWebServer server(80);
AsyncWebSocket ws("/ws");
const char index_html[] PROGMEM = R"rawliteral(
<!DOCTYPE HTML><html>
<head>
<title>ESP Web Server</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="icon" href="data:,">
<style>
html {
font-family: Arial, Helvetica, sans-serif;
text-align: center;
}
h1 {
font-size: 1.8rem;
color: white;
}
h2{
font-size: 1.5rem;
font-weight: bold;
color: #143642;
}
.topnav {
overflow: hidden;
background-color: #143642;
}
body {
margin: 0;
}
.content {
padding: 30px;
max-width: 600px;
margin: 0 auto;
}
.card {
background-color: #F8F7F9;;
box-shadow: 2px 2px 12px 1px rgba(140,140,140,.5);
padding-top:10px;
padding-bottom:20px;
}
.button {
padding: 15px 50px;
font-size: 24px;
text-align: center;
outline: none;
color: #fff;
background-color: #0f8b8d;
border: none;
border-radius: 5px;
-webkit-touch-callout: none;
-webkit-user-select: none;
-khtml-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
-webkit-tap-highlight-color: rgba(0,0,0,0);
}
/*.button:hover {background-color: #0f8b8d}*/
.button:active {
background-color: #0f8b8d;
box-shadow: 2 2px #CDCDCD;
transform: translateY(2px);
}
.state {
font-size: 1.5rem;
color:#8c8c8c;
font-weight: bold;
}
</style>
<title>ESP Web Server</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="icon" href="data:,">
</head>
<body>
<div class="topnav">
<h1>ESP WebSocket Server</h1>
</div>
<div class="content">
<div class="card">
<h2>Output - GPIO 2</h2>
<p class="state">state: <span id="state">%STATE%</span></p>
<p><button id="button" class="button">Toggle</button></p>
</div>
</div>
<script>
var gateway = `ws://${window.location.hostname}/ws`;
var websocket;
window.addEventListener('load', onLoad);
function initWebSocket() {
console.log('Trying to open a WebSocket connection...');
websocket = new WebSocket(gateway);
websocket.onopen = onOpen;
websocket.onclose = onClose;
websocket.onmessage = onMessage; // <-- add this line
}
function onOpen(event) {
console.log('Connection opened');
}
function onClose(event) {
console.log('Connection closed');
setTimeout(initWebSocket, 2000);
}
function onMessage(event) {
var state;
if (event.data == "1"){
state = "ON";
}
else{
state = "OFF";
}
document.getElementById('state').innerHTML = state;
}
function onLoad(event) {
initWebSocket();
initButton();
}
function initButton() {
document.getElementById('button').addEventListener('click', toggle);
}
function toggle(){
websocket.send('toggle');
}
</script>
</body>
</html>
)rawliteral";
void notifyClients() {
ws.textAll(String(ledState));
}
void handleWebSocketMessage(void *arg, uint8_t *data, size_t len) {
AwsFrameInfo *info = (AwsFrameInfo*)arg;
if (info->final && info->index == 0 && info->len == len && info->opcode == WS_TEXT) {
data[len] = 0;
if (strcmp((char*)data, "toggle") == 0) {
ledState = !ledState;
notifyClients();
}
}
}
void onEvent(AsyncWebSocket *server, AsyncWebSocketClient *client, AwsEventType type,
void *arg, uint8_t *data, size_t len) {
switch (type) {
case WS_EVT_CONNECT:
Serial.printf("WebSocket client #%u connected from %s\n", client->id(), client->remoteIP().toString().c_str());
break;
case WS_EVT_DISCONNECT:
Serial.printf("WebSocket client #%u disconnected\n", client->id());
break;
case WS_EVT_DATA:
handleWebSocketMessage(arg, data, len);
break;
case WS_EVT_PONG:
case WS_EVT_ERROR:
break;
}
}
void initWebSocket() {
ws.onEvent(onEvent);
server.addHandler(&ws);
}
String processor(const String& var){
Serial.println(var);
if(var == "STATE"){
if (ledState){
return "ON";
}
else{
return "OFF";
}
}
return String();
}
void setup(){
// Serial port for debugging purposes
Serial.begin(115200);
pinMode(ledPin, OUTPUT);
digitalWrite(ledPin, LOW);
// Connect to Wi-Fi
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
Serial.println("Connecting to WiFi..");
}
// Print ESP Local IP Address
Serial.println(WiFi.localIP());
initWebSocket();
// Route for root / web page
server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){
request->send_P(200, "text/html", index_html, processor);
});
// Start server
server.begin();
}
void loop() {
ws.cleanupClients();
digitalWrite(ledPin, ledState);
}
Insérez vos informations d’identification réseau dans les variables suivantes et le code fonctionnera immédiatement.
const char* ssid = "REPLACE_WITH_YOUR_SSID";
const char* password = "REPLACE_WITH_YOUR_PASSWORD";
Comment fonctionne le code
Continuez à lire pour savoir comment le code fonctionne ou passez à la Manifestation section.
Importation de bibliothèques
Importez les bibliothèques nécessaires pour créer le serveur Web.
#include <WiFi.h>
#include <AsyncTCP.h>
#include <ESPAsyncWebServer.h>
Informations d’identification réseau
Insérez vos identifiants réseau dans les variables suivantes :
const char* ssid = "REPLACE_WITH_YOUR_SSID";
const char* password = "REPLACE_WITH_YOUR_PASSWORD";
Sortie GPIO
Créez une variable appelée ledState pour contenir l’état du GPIO et une variable appelée ledPin qui fait référence au GPIO que vous souhaitez contrôler. Dans ce cas, nous contrôlerons la LED intégrée (qui est connectée au GPIO 2).
bool ledState = 0;
const int ledPin = 2;
AsyncWebServer et AsyncWebSocket
Créez un objet AsyncWebServer sur le port 80.
AsyncWebServer server(80);
La bibliothèque ESPAsyncWebServer inclut un plugin WebSocket qui facilite la gestion des connexions WebSocket. Créez un objet AsyncWebSocket appelé ws pour gérer les connexions sur le chemin /ws.
AsyncWebSocket ws("/ws");
Construire la page Web
La variable index_html contient le code HTML, CSS et JavaScript nécessaires pour créer et styliser la page Web et gérer les interactions client-serveur à l’aide du protocole WebSocket.
Remarque : nous plaçons tout ce qui est nécessaire pour construire la page Web sur la variable index_html que nous utilisons sur l’esquisse Arduino. Notez qu’il peut être plus pratique d’avoir des fichiers HTML, CSS et JavaScript séparés que vous téléchargez ensuite sur le système de fichiers ESP32 et que vous les référencez dans le code.
Lecture recommandée : Serveur Web ESP32 utilisant SPIFFS (SPI Flash File System)
Voici le contenu de la variable index_html :
<!DOCTYPE HTML>
<html>
<head>
<title>ESP Web Server</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="icon" href="data:,">
<style>
html {
font-family: Arial, Helvetica, sans-serif;
text-align: center;
}
h1 {
font-size: 1.8rem;
color: white;
}
h2{
font-size: 1.5rem;
font-weight: bold;
color: #143642;
}
.topnav {
overflow: hidden;
background-color: #143642;
}
body {
margin: 0;
}
.content {
padding: 30px;
max-width: 600px;
margin: 0 auto;
}
.card {
background-color: #F8F7F9;;
box-shadow: 2px 2px 12px 1px rgba(140,140,140,.5);
padding-top:10px;
padding-bottom:20px;
}
.button {
padding: 15px 50px;
font-size: 24px;
text-align: center;
outline: none;
color: #fff;
background-color: #0f8b8d;
border: none;
border-radius: 5px;
-webkit-touch-callout: none;
-webkit-user-select: none;
-khtml-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
-webkit-tap-highlight-color: rgba(0,0,0,0);
}
.button:active {
background-color: #0f8b8d;
box-shadow: 2 2px #CDCDCD;
transform: translateY(2px);
}
.state {
font-size: 1.5rem;
color:#8c8c8c;
font-weight: bold;
}
</style>
<title>ESP Web Server</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="icon" href="data:,">
</head>
<body>
<div class="topnav">
<h1>ESP WebSocket Server</h1>
</div>
<div class="content">
<div class="card">
<h2>Output - GPIO 2</h2>
<p class="state">state: <span id="state">%STATE%</span></p>
<p><button id="button" class="button">Toggle</button></p>
</div>
</div>
<script>
var gateway = `ws://${window.location.hostname}/ws`;
var websocket;
function initWebSocket() {
console.log('Trying to open a WebSocket connection...');
websocket = new WebSocket(gateway);
websocket.onopen = onOpen;
websocket.onclose = onClose;
websocket.onmessage = onMessage; // <-- add this line
}
function onOpen(event) {
console.log('Connection opened');
}
function onClose(event) {
console.log('Connection closed');
setTimeout(initWebSocket, 2000);
}
function onMessage(event) {
var state;
if (event.data == "1"){
state = "ON";
}
else{
state = "OFF";
}
document.getElementById('state').innerHTML = state;
}
window.addEventListener('load', onLoad);
function onLoad(event) {
initWebSocket();
initButton();
}
function initButton() {
document.getElementById('button').addEventListener('click', toggle);
}
function toggle(){
websocket.send('toggle');
}
</script>
</body>
</html>
CSS
Entre les balises
, nous incluons les styles pour styliser la page Web à l’aide de CSS. N’hésitez pas à le modifier pour que la page Web s’affiche comme vous le souhaitez. Nous n’expliquerons pas le fonctionnement du CSS de cette page Web car il n’est pas pertinent pour ce didacticiel WebSocket.
<style>
html {
font-family: Arial, Helvetica, sans-serif;
text-align: center;
}
h1 {
font-size: 1.8rem;
color: white;
}
h2 {
font-size: 1.5rem;
font-weight: bold;
color: #143642;
}
.topnav {
overflow: hidden;
background-color: #143642;
}
body {
margin: 0;
}
.content {
padding: 30px;
max-width: 600px;
margin: 0 auto;
}
.card {
background-color: #F8F7F9;;
box-shadow: 2px 2px 12px 1px rgba(140,140,140,.5);
padding-top:10px;
padding-bottom:20px;
}
.button {
padding: 15px 50px;
font-size: 24px;
text-align: center;
outline: none;
color: #fff;
background-color: #0f8b8d;
border: none;
border-radius: 5px;
-webkit-touch-callout: none;
-webkit-user-select: none;
-khtml-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
-webkit-tap-highlight-color: rgba(0,0,0,0);
}
.button:active {
background-color: #0f8b8d;
box-shadow: 2 2px #CDCDCD;
transform: translateY(2px);
}
.state {
font-size: 1.5rem;
color:#8c8c8c;
font-weight: bold;
}
</style>
HTML
Entre les balises
, nous ajoutons le contenu de la page Web visible par l’utilisateur.<div class="topnav">
<h1>ESP WebSocket Server</h1>
</div>
<div class="content">
<div class="card">
<h2>Output - GPIO 2</h2>
<p class="state">state: <span id="state">%STATE%</span></p>
<p><button id="button" class="button">Toggle</button></p>
</div>
</div>
Il y a un titre 1 avec le texte « ESP WebSocket Server ». N’hésitez pas à modifier ce texte.
<h1>ESP WebSocket Server</h1>
Ensuite, il y a un titre 2 avec le texte « Sortie – GPIO 2 ».
<h2>Output - GPIO 2</h2>
Après cela, nous avons un paragraphe qui affiche l’état GPIO actuel.
<p class="state">state: <span id="state">%STATE%</span></p>
Le %STATE% est un espace réservé pour l’état GPIO. Elle sera remplacée par la valeur actuelle par l’ESP32 au moment de l’envoi de la page web. Les espaces réservés sur le texte HTML doivent être entre les signes %. Cela signifie que ce texte %STATE% est comme une variable qui sera ensuite remplacée par la valeur réelle.
Après avoir envoyé la page Web au client, l’état doit changer dynamiquement chaque fois qu’il y a un changement dans l’état GPIO. Nous recevrons ces informations via le protocole WebSocket. Ensuite, JavaScript gère ce qu’il faut faire avec les informations reçues pour mettre à jour l’état en conséquence. Pour pouvoir gérer ce texte à l’aide de JavaScript, le texte doit avoir un identifiant que nous pouvons référencer. Dans ce cas, l’identifiant est l’état ( ).
Enfin, il y a un paragraphe avec le bouton pour basculer l’état GPIO.
<p><button id="button" class="button">Toggle</button></p>
Notez que nous avons donné un identifiant au bouton ( id= »bouton »).
JavaScript – Gestion des WebSockets
Le JavaScript se place entre les balises . Il est chargé d’initialiser une connexion WebSocket avec le serveur dès que l’interface Web est entièrement chargée dans le navigateur et de gérer l’échange de données via WebSockets.
<script>
var gateway = `ws://${window.location.hostname}/ws`;
var websocket;
function initWebSocket() {
console.log('Trying to open a WebSocket connection...');
websocket = new WebSocket(gateway);
websocket.onopen = onOpen;
websocket.onclose = onClose;
websocket.onmessage = onMessage; // <-- add this line
}
function onOpen(event) {
console.log('Connection opened');
}
function onClose(event) {
console.log('Connection closed');
setTimeout(initWebSocket, 2000);
}
function onMessage(event) {
var state;
if (event.data == "1"){
state = "ON";
}
else{
state = "OFF";
}
document.getElementById('state').innerHTML = state;
}
window.addEventListener('load', onLoad);
function onLoad(event) {
initWebSocket();
initButton();
}
function initButton() {
document.getElementById('button').addEventListener('click', toggle);
}
function toggle(){
websocket.send('toggle');
}
</script>
Voyons comment cela fonctionne.
La passerelle est le point d’entrée de l’interface WebSocket.
var gateway = `ws://${window.location.hostname}/ws`;
window.location.hostname obtient l’adresse de la page actuelle (l’adresse IP du serveur Web).
Créez une nouvelle variable globale appelée websocket.
var websocket;
Ajoutez un écouteur d’événement qui appellera la fonction onload lors du chargement de la page Web.
window.addEventListener('load', onload);
La fonction onload() appelle la fonction initWebSocket() pour initialiser une connexion WebSocket avec le serveur et la fonction initButton() pour ajouter des écouteurs d’événement aux boutons.
function onload(event) {
initWebSocket();
initButton();
}
La fonction initWebSocket() initialise une connexion WebSocket sur la passerelle définie précédemment. Nous attribuons également plusieurs fonctions de rappel lorsque la connexion WebSocket est ouverte, fermée ou lorsqu’un message est reçu.
function initWebSocket() {
console.log('Trying to open a WebSocket connection…');
websocket = new WebSocket(gateway);
websocket.onopen = onOpen;
websocket.onclose = onClose;
websocket.onmessage = onMessage;
}
Lorsque la connexion est ouverte, nous imprimons simplement un message dans la console et envoyons un message disant « salut ». L’ESP32 reçoit ce message, nous savons donc que la connexion a été initialisée.
function onOpen(event) {
console.log('Connection opened');
websocket.send('hi');
}
Si pour une raison quelconque la connexion web socket est fermée, nous appelons à nouveau la fonction initWebSocket() après 2000 millisecondes (2 secondes).
function onClose(event) {
console.log('Connection closed');
setTimeout(initWebSocket, 2000);
}
La méthode setTimeout() appelle une fonction ou évalue une expression après un nombre spécifié de millisecondes.
Enfin, nous devons gérer ce qui se passe lorsque nous recevons un nouveau message. Le serveur (votre carte ESP) enverra soit un message « 1 » soit un message « 0 ». En fonction du message reçu, on veut afficher un message « ON » ou « OFF » sur le paragraphe qui affiche l’état. Vous souvenez-vous de cette balise avec id= »state » ? Nous obtiendrons cet élément et définirons sa valeur sur ON ou OFF.
function onMessage(event) {
var state;
if (event.data == "1"){
state = "ON";
}
else{
state = "OFF";
}
document.getElementById('state').innerHTML = state;
}
La fonction initButton() récupère le bouton par son identifiant (bouton) et ajoute un écouteur d’événement de type ‘click’.
function initButton() {
document.getElementById('button').addEventListener('click', toggle);
}
Cela signifie que lorsque vous cliquez sur le bouton, la fonction bascule est appelée.
La fonction bascule envoie un message à l’aide de la connexion WebSocket avec le texte « bascule ».
function toggle(){
websocket.send('toggle');
}
Ensuite, l’ESP32 doit gérer ce qui se passe lorsqu’il reçoit ce message – basculer l’état GPIO actuel.
Gestion des WebSockets – Serveur
Auparavant, vous avez vu comment gérer la connexion WebSocket côté client (navigateur). Voyons maintenant comment le gérer côté serveur.
Aviser tous les clients
La fonction notifyClients() notifie tous les clients avec un message contenant tout ce que vous transmettez comme argument. Dans ce cas, nous voudrons informer tous les clients de l’état actuel de la LED chaque fois qu’il y a un changement.
void notifyClients() {
ws.textAll(String(ledState));
}
La classe AsyncWebSocket fournit une méthode textAll() pour envoyer le même message à tous les clients connectés au serveur en même temps.
Gérer les messages WebSocket
La fonction handleWebSocketMessage() est une fonction de rappel qui s’exécute chaque fois que nous recevons de nouvelles données des clients via le protocole WebSocket.
void handleWebSocketMessage(void *arg, uint8_t *data, size_t len) {
AwsFrameInfo *info = (AwsFrameInfo*)arg;
if (info->final && info->index == 0 && info->len == len && info->opcode == WS_TEXT) {
data[len] = 0;
if (strcmp((char*)data, "toggle") == 0) {
ledState = !ledState;
notifyClients();
}
}
}
Si nous recevons le message « toggle », nous basculons la valeur de la variable ledState. De plus, nous notifions tous les clients en appelant la fonction notifyClients(). De cette façon, tous les clients sont informés du changement et mettent à jour l’interface en conséquence.
if (strcmp((char*)data, "toggle") == 0) {
ledState = !ledState;
notifyClients();
}
Configurer le serveur WebSocket
Nous devons maintenant configurer un écouteur d’événement pour gérer les différentes étapes asynchrones du protocole WebSocket. Ce gestionnaire d’événements peut être implémenté en définissant onEvent() comme suit :
void onEvent(AsyncWebSocket *server, AsyncWebSocketClient *client, AwsEventType type,
void *arg, uint8_t *data, size_t len) {
switch (type) {
case WS_EVT_CONNECT:
Serial.printf("WebSocket client #%u connected from %s\n", client->id(), client->remoteIP().toString().c_str());
break;
case WS_EVT_DISCONNECT:
Serial.printf("WebSocket client #%u disconnected\n", client->id());
break;
case WS_EVT_DATA:
handleWebSocketMessage(arg, data, len);
break;
case WS_EVT_PONG:
case WS_EVT_ERROR:
break;
}
}
L’argument type représente l’événement qui se produit. Il peut prendre les valeurs suivantes :
- WS_EVT_CONNECT lorsqu’un client s’est connecté ;
- WS_EVT_DISCONNECT lorsqu’un client s’est déconnecté ;
- WS_EVT_DATA lorsqu’un paquet de données est reçu du client ;
- WS_EVT_PONG en réponse à une requête ping ;
- WS_EVT_ERROR lorsqu’une erreur est reçue du client.
Initialiser WebSocket
Enfin, la fonction initWebSocket() initialise le protocole WebSocket.
void initWebSocket() {
ws.onEvent(onEvent);
server.addHandler(&ws);
}
processeur()
La fonction processor() est chargée de rechercher des espaces réservés sur le texte HTML et de les remplacer par ce que nous voulons avant d’envoyer la page Web au navigateur. Dans notre cas, nous remplacerons l’espace réservé %STATE% par ON si le ledState est 1. Sinon, remplacez-le par OFF.
String processor(const String& var){
Serial.println(var);
if(var == "STATE"){
if (ledState){
return "ON";
}
else{
return "OFF";
}
}
}
installation()
Dans setup(), initialisez le moniteur série à des fins de débogage.
Serial.begin(115200);
Configurez le ledPin en tant que SORTIE et réglez-le sur BAS lorsque le programme démarre pour la première fois.
pinMode(ledPin, OUTPUT);
digitalWrite(ledPin, LOW);
Initialisez le Wi-Fi et imprimez l’adresse IP ESP32 sur le moniteur série.
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(1000);
Serial.println("Connecting to WiFi..");
}
// Print ESP Local IP Address
Serial.println(WiFi.localIP());
Initialisez le protocole WebSocket en appelant la fonction initWebSocket() créée précédemment.
initWebSocket();
Traiter les demandes
Servez le texte enregistré sur la variable index_html lorsque vous recevez une demande sur la root / l’URL – vous devez transmettre la fonction de processeur en tant qu’argument pour remplacer les espaces réservés par l’état GPIO actuel.
server.on("/", HTTP_GET, [](AsyncWebServerRequest *request){
request->send_P(200, "text/html", index_html, processor);
});
Enfin, démarrez le serveur.
server.begin();
boucle()
La LED sera contrôlée physiquement sur la boucle().
void loop() {
ws.cleanupClients();
digitalWrite(ledPin, ledState);
}
Notez que nous appelons tous la méthode cleanupClients(). Voici pourquoi (explication de la page GitHub de la bibliothèque ESPAsyncWebServer):
Les navigateurs ne ferment parfois pas correctement la connexion WebSocket, même lorsque la fonction close() est appelée en JavaScript. Cela finira par épuiser les ressources du serveur Web et entraînera le blocage du serveur. L’appel périodique de la fonction cleanupClients() depuis la boucle principale() limite le nombre de clients en fermant le client le plus ancien lorsque le nombre maximum de clients a été dépassé. Cela peut être appelé à chaque cycle, cependant, si vous souhaitez utiliser moins d’énergie, il suffit d’appeler aussi rarement qu’une fois par seconde.
Manifestation
Après avoir inséré vos informations d’identification réseau sur les variables ssid et mot de passe, vous pouvez télécharger le code sur votre carte. N’oubliez pas de vérifier si vous avez sélectionné la bonne carte et le bon port COM.
Après avoir téléchargé le code, ouvrez le moniteur série à un débit en bauds de 115200 et appuyez sur le bouton EN/RST intégré. L’adresse IP ESP doit être imprimée.
Ouvrez un navigateur sur votre réseau local et insérez l’adresse IP ESP32. Vous devriez avoir accès à la page Web pour contrôler la sortie.

Cliquez sur le bouton pour basculer la LED. Vous pouvez ouvrir plusieurs onglets de navigateur Web en même temps ou accéder au serveur Web à partir de différents appareils et l’état de la LED sera automatiquement mis à jour dans tous les clients chaque fois qu’il y a un changement.
Conclusion
Dans ce tutoriel, vous avez appris à configurer un serveur WebSocket avec l’ESP32. Le protocole WebSocket permet une communication en duplex intégral entre le client et le serveur. Après l’initialisation, le serveur et le client peuvent échanger des données à tout moment.
Ceci est très utile car le serveur peut envoyer des données au client chaque fois que quelque chose se passe. Par exemple, vous pouvez ajouter un bouton physique à cette configuration qui, lorsqu’il est enfoncé, avertit tous les clients de mettre à jour l’interface Web.
Dans cet exemple, nous vous avons montré comment contrôler un GPIO de l’ESP32. Vous pouvez utiliser cette méthode pour contrôler plus de GPIO. Vous pouvez également utiliser le protocole WebSocket pour envoyer des lectures de capteurs ou des notifications à tout moment.
Nous espérons que vous avez trouvé ce tutoriel utile. Nous avons l’intention de créer plus de tutoriels et d’exemples en utilisant le protocole WebSocket. Alors restez à l’écoute.
En savoir plus sur l’ESP32 avec nos ressources :
Cette vidéo vous emmène dans l’histoire de Raspberry Pi :

-
Lot de 3 cartes de développement ESP32 DevKitC ESP32 ESP32-WROOM-32U WiFi Bluetooth pour Arduino IDELot de 3 cartes mères ESP32 DevKitC ESP32 ESP32-WROOM-32U pour Arduino IDE Consommation d'énergie ultra faible, fonctionne parfaitement avec l'Arduino IDE. ESP32 est sécurisé, fiable et évolutif pour une grande variété d'applications. Les développeurs peuvent connecter des périphériques à des câbles de pontage ou monter ESP32-DevKitC V4 sur une planche à découper. Câble d'ordinateur USB A / Micro USB B