Raspberry Pi Pico W Wi-Fi : créer un serveur web en MicroPython
Raspberry Pi Pico W et Wi-Fi : le bon UF2, network.WLAN et codes d'état, serveur web pour une LED, capteurs en direct, API avec urequests et heure par NTP.
Utiliser le Wi-Fi du Raspberry Pi Pico W est l'un des moyens les moins chers et les plus simples de fabriquer un petit appareil que tu pilotes depuis ton téléphone. Le Pico W est la version du célèbre Raspberry Pi Pico qui ajoute le Wi-Fi 2,4 GHz et le Bluetooth : avec quelques lignes de MicroPython, il rejoint ton réseau domestique, sert sa propre page web et récupère la météo et l'heure sur internet. Dans ce guide, tu vas connecter un Pico W au Wi-Fi en partant de zéro, créer un serveur web qui allume une LED depuis ton téléphone, puis une page qui affiche les données d'un capteur en direct.
À la fin, tu sauras choisir le bon fichier UF2, te connecter avec network.WLAN et lire ses codes d'état, récupérer des données d'une API avec urequests, régler l'heure par NTP et faire la même chose dans l'Arduino IDE. Si tu découvres le Pico, commence par Qu'est-ce que le Raspberry Pi Pico ? ; les commandes de base sont expliquées dans le guide Qu'est-ce que MicroPython ?.

Qu'est-ce que le Raspberry Pi Pico W et en quoi diffère-t-il du Pico ?
Le Pico W reprend le même processeur RP2040, la même taille et le même brochage à 40 broches que le Pico. La différence, c'est la puce sans fil Infineon CYW43439 ajoutée sur la carte : elle apporte le Wi-Fi 802.11n à 2,4 GHz et le Bluetooth 5.2. Le processeur dialogue avec cette puce via une liaison SPI interne ; toi, tu utilises seulement le module network de MicroPython. Raspberry Pi a ensuite lancé le Pico 2 W avec le processeur RP2350 ; comme la puce sans fil est la même, tout le code de cet article fonctionne aussi dessus.
| Caractéristique | Pico W | Pico 2 W | ESP32 (WROOM-32) |
|---|---|---|---|
| Processeur | RP2040, double cœur Cortex-M0+, 133 MHz | RP2350, double cœur Cortex-M33 (ou RISC-V), 150 MHz | Xtensa LX6, double cœur, 240 MHz |
| RAM | 264 Ko | 520 Ko | 520 Ko |
| Mémoire flash | 2 Mo | 4 Mo | Généralement 4 Mo |
| Wi-Fi | 2,4 GHz, 802.11n (CYW43439) | 2,4 GHz, 802.11n (CYW43439) | 2,4 GHz, 802.11 b/g/n (intégré à la puce) |
| Bluetooth | 5.2 (Classic et BLE) | 5.2 (Classic et BLE) | 4.2 (Classic et BLE) |
| Entrées analogiques | 3 canaux, 12 bits | 3 canaux, 12 bits | 18 canaux, 12 bits |
| Fichier MicroPython | RPI_PICO_W (.uf2) | RPI_PICO2_W (.uf2) | ESP32_GENERIC (.bin) |
Sur le papier, l'ESP32 est plus rapide et dispose de plus d'exemples dans l'univers Arduino. Les atouts du Pico W sont un support MicroPython officiel et mûr, une documentation bien rangée et des broches sans pièges du genre « doit être à tel niveau au démarrage ». Si tu aimes apprendre avec Python, le Pico W est un excellent choix ; si le code Arduino et les bibliothèques toutes prêtes comptent avant tout pour toi, l'ESP32 sera peut-être plus confortable. Si tu hésites entre les deux, le comparatif Arduino ou ESP32 ? t'aidera à choisir.
La puce sans fil du Pico W et les différences de broches
Les broches accessibles du Pico W sont exactement les mêmes que sur le Pico : GP0–GP22 et GP26–GP28 sont libres, et les entrées analogiques restent sur GP26, GP27 et GP28. Ce qui change, ce sont les quatre broches qui restent à l'intérieur de la carte. Sur le Pico, elles gèrent la LED intégrée, le mode de l'alimentation et la détection USB ; sur le Pico W, elles sont réservées au dialogue avec la puce sans fil, et la LED est reliée directement à cette puce. Tu peux voir le brochage complet de la carte dans l'outil Pinout.
| Broche interne | Rôle sur le Pico | Rôle sur le Pico W |
|---|---|---|
| GP23 | Mode de l'alimentation (SMPS) | Activation de la puce sans fil (WL_ON) |
| GP24 | Détection de la tension USB (VBUS) | Ligne de données et d'interruption sans fil (WL_D) |
| GP25 | LED intégrée | Sélection de la puce sans fil (WL_CS) |
| GP29 | Mesure de la tension VSYS (ADC3) | Horloge sans fil (WL_CLK) et mesure de VSYS |
| LED intégrée | GP25 : Pin(25) | WL_GPIO0 de la puce sans fil : Pin("LED") |
Étape 1 : flasher le bon fichier UF2 pour le Pico W
L'erreur la plus courante consiste à flasher sur un Pico W le fichier MicroPython du Pico classique. La carte fonctionne et tu vois l'invite dans le Shell de Thonny, mais dès que tu tapes import network, tu obtiens « ImportError: no module named 'network' », car la version pour le Pico classique ne contient pas le pilote sans fil. Chaque carte a son propre fichier UF2 :
| Carte | Fichier UF2 MicroPython | Lecteur affiché en mode BOOTSEL |
|---|---|---|
| Raspberry Pi Pico | RPI_PICO-….uf2 | RPI-RP2 |
| Raspberry Pi Pico W / WH | RPI_PICO_W-….uf2 | RPI-RP2 |
| Raspberry Pi Pico 2 | RPI_PICO2-….uf2 | RP2350 |
| Raspberry Pi Pico 2 W | RPI_PICO2_W-….uf2 | RP2350 |
- Sur la page de téléchargement de micropython.org, trouve la carte RPI_PICO_W (RPI_PICO2_W pour le Pico 2 W) et télécharge le dernier fichier .uf2 stable, celui qui n'est pas marqué « preview ».
- Maintiens le bouton BOOTSEL du Pico W enfoncé pendant que tu branches le câble USB de données sur l'ordinateur, puis relâche-le.
- Un lecteur nommé RPI-RP2 apparaît sur l'ordinateur. Glisse le fichier téléchargé dessus ; une fois la copie terminée, le lecteur disparaît tout seul et la carte redémarre sous MicroPython.
- Ouvre Thonny et choisis MicroPython (Raspberry Pi Pico) dans le menu de l'interpréteur, en bas à droite. Si tu préfères, la fenêtre « Install or update MicroPython » de Thonny fait la même installation en un clic quand tu choisis la variante Pico W / Pico WH.
- Tape import network dans le Shell. S'il n'y a pas d'erreur, le bon firmware avec prise en charge du sans-fil est installé.
Étape 2 : se connecter au Wi-Fi avec network.WLAN
Le Pico W possède deux interfaces sans fil : en mode WLAN.IF_STA (station), il se connecte à ta box comme un téléphone ; en mode WLAN.IF_AP (point d'accès), il crée son propre réseau Wi-Fi. Commençons par le mode station. Colle le code ci-dessous dans un nouveau fichier de Thonny, saisis le nom de ton réseau et ton mot de passe, puis enregistre-le sur le Pico sous le nom wifi.py. Tous les exemples suivants utilisent ce fichier avec import wifi : ton mot de passe ne se trouve ainsi qu'à un seul endroit. Si tu utilises une version de MicroPython antérieure à la 1.24, écris ces constantes network.STA_IF et network.AP_IF ; les anciens noms fonctionnent aussi dans les versions récentes.
1# wifi.py: Pico W'ye bu adla kaydet / save it to the Pico W with this name
2import network
3import time
4
5SSID = "AgAdi" # Wi-Fi adın / your Wi-Fi name
6PASSWORD = "Sifre123" # Wi-Fi şifren / your Wi-Fi password
7HOSTNAME = "picow" # http://picow.local adresi için / for http://picow.local
8
9STATUS = {
10 0: "Boşta / idle",
11 1: "Ağa katılıyor / joining",
12 2: "IP bekleniyor / waiting for IP",
13 3: "Bağlandı / connected",
14 -1: "Bağlantı başarısız / connection failed",
15 -2: "Ağ bulunamadı / network not found",
16 -3: "Şifre hatalı / wrong password",
17}
18
19
20def connect(timeout=20):
21 network.country("TR") # ülke kodu / country code
22 network.hostname(HOSTNAME) # ağdaki adı / name on the network
23 wlan = network.WLAN(network.WLAN.IF_STA)
24 wlan.active(True)
25 wlan.config(pm=network.WLAN.PM_NONE) # güç tasarrufunu kapat / disable power saving
26 if not wlan.isconnected():
27 wlan.connect(SSID, PASSWORD)
28 for _ in range(timeout):
29 code = wlan.status()
30 print(code, STATUS.get(code, "?"))
31 if code < 0 or code == 3:
32 break
33 time.sleep(1)
34 if wlan.status() != 3:
35 raise RuntimeError("Wi-Fi: " + STATUS.get(wlan.status(), "?"))
36 print("IP:", wlan.ifconfig()[0])
37 return wlan
38
39
40if __name__ == "__main__":
41 connect()Regardons les lignes importantes. network.country("TR") indique à la puce sans fil les règles de canaux de quel pays respecter ; remplace TR par le code de ton pays, par exemple FR, BE ou CH. Sinon, tu risques d'avoir du mal à voir les réseaux sur les canaux 12 et 13, utilisés par certaines box (les anciens firmwares font la même chose avec rp2.country()). wlan.config(pm=network.WLAN.PM_NONE) désactive l'économie d'énergie (les anciens exemples écrivent le même réglage pm=0xa11140) : par défaut, le Pico W économise l'énergie, ce qui peut retarder les réponses du serveur web ou couper la connexion au bout de quelques heures. La boucle affiche le code d'état chaque seconde et s'arrête dès qu'elle atteint 3 ou reçoit un code d'erreur négatif. Ainsi, la carte n'attend jamais indéfiniment et tu vois à l'écran ce qui ne va pas.
Que signifient les codes de wlan.status() ?
La plupart des problèmes de connexion se règlent en quelques secondes en regardant le nombre renvoyé par wlan.status(). MicroPython propose aussi des constantes toutes prêtes pour ces nombres dans le module network ; tu trouveras les deux dans le tableau ci-dessous :
| Code | Constante | Signification | Que faire ? |
|---|---|---|---|
| 0 | STAT_IDLE | Aucune connexion, rien n'a démarré | Vérifie que wlan.active(True) et wlan.connect() ont bien été appelés |
| 1 | STAT_CONNECTING | Connexion au réseau en cours | Attends quelques secondes |
| 2 | (pas de constante) | Associé au réseau, attend une adresse IP de la box | Si cela dure, vérifie le DHCP de la box |
| 3 | STAT_GOT_IP | Connecté avec une adresse IP | Tout est prêt |
| -1 | STAT_CONNECT_FAIL | Échec de la connexion | Vérifie le signal et l'alimentation, puis réessaie |
| -2 | STAT_NO_AP_FOUND | Réseau introuvable | Vérifie le nom du réseau, la bande 2,4 GHz et la distance |
| -3 | STAT_WRONG_PASSWORD | Échec de l'authentification | Ressaisis le mot de passe en respectant majuscules et minuscules |
Si tu obtiens le code -2, le Pico W ne voit pas ton réseau. Lister les réseaux alentour révèle tout de suite le problème : si le tien n'apparaît pas, soit il émet en 5 GHz, soit le signal est trop faible. Un RSSI meilleur que -70 dBm (par exemple -55 dBm) est confortable ; vers -80 dBm, la connexion commence à décrocher.
1import network
2
3wlan = network.WLAN(network.WLAN.IF_STA)
4wlan.active(True)
5for ssid, bssid, channel, rssi, security, hidden in wlan.scan():
6 print(ssid.decode(), "| kanal / channel:", channel, "| RSSI:", rssi, "dBm")Étape 3 : un serveur web simple en MicroPython (page pour allumer et éteindre une LED)
Transformons maintenant le Pico W en petit serveur web que tu peux ouvrir depuis ton téléphone. Aucune bibliothèque supplémentaire n'est nécessaire : le module socket de MicroPython suffit. Enregistre le code ci-dessous sous le nom main.py et lance-le. Saisis l'adresse affichée dans le Shell (par exemple http://192.168.1.42) dans le navigateur d'un téléphone connecté au même réseau Wi-Fi ; les boutons ON et OFF de la page allument et éteignent la LED de la carte.
1import socket
2from machine import Pin
3import wifi
4
5wlan = wifi.connect()
6led = Pin("LED", Pin.OUT) # Pico W dahili LED / Pico W onboard LED
7led_on = False
8
9
10def page(on):
11 state = "AÇIK / ON" if on else "KAPALI / OFF"
12 return """<!DOCTYPE html>
13<html><head><meta charset="utf-8">
14<meta name="viewport" content="width=device-width, initial-scale=1">
15<title>Pico W LED</title></head>
16<body style="font-family:sans-serif;text-align:center">
17<h1>Pico W LED</h1>
18<p>Durum / State: <b>""" + state + """</b></p>
19<p><a href="/on"><button style="font-size:24px">AÇ / ON</button></a>
20<a href="/off"><button style="font-size:24px">KAPAT / OFF</button></a></p>
21</body></html>"""
22
23
24addr = socket.getaddrinfo("0.0.0.0", 80)[0][-1]
25server = socket.socket()
26server.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) # EADDRINUSE hatasını önler / prevents EADDRINUSE
27server.bind(addr)
28server.listen(2)
29print("Tarayıcıda aç / open in browser: http://" + wlan.ifconfig()[0])
30
31while True:
32 client, remote = server.accept() # bir tarayıcı bekle / wait for a browser
33 try:
34 request = client.recv(1024) # b"GET /on HTTP/1.1 ..."
35 parts = request.split(b" ")
36 path = parts[1] if len(parts) > 1 else b"/"
37 if path == b"/on":
38 led.on()
39 led_on = True
40 elif path == b"/off":
41 led.off()
42 led_on = False
43 if path in (b"/", b"/on", b"/off"):
44 client.sendall("HTTP/1.0 200 OK\r\nContent-Type: text/html; charset=utf-8\r\n\r\n")
45 client.sendall(page(led_on))
46 else:
47 client.sendall("HTTP/1.0 404 Not Found\r\n\r\n") # ör. /favicon.ico / e.g. /favicon.ico
48 except OSError as e:
49 print("Bağlantı hatası / connection error:", e)
50 finally:
51 client.close()Voyons comment cela fonctionne. Avec bind et listen, le Pico W écoute le port 80 (HTTP), et accept() attend qu'un navigateur se connecte. La première ligne de la requête du navigateur ressemble à « GET /on HTTP/1.1 » ; le code la découpe aux espaces pour trouver le chemin demandé (/on) et règle la LED en conséquence. Il envoie ensuite l'en-tête HTTP (« HTTP/1.0 200 OK » et le type de contenu), une ligne vide et enfin la page HTML, puis ferme la connexion. La ligne meta viewport adapte correctement la page à l'écran du téléphone, et charset=utf-8 garantit l'affichage correct des accents.
| Chemin | Ce qu'il fait |
|---|---|
| / | Affiche la page et l'état actuel de la LED |
| /on | Allume la LED et renvoie la page |
| /off | Éteint la LED et renvoie la page |
| /favicon.ico et autres | Renvoie 404 ; les navigateurs demandent ce chemin d'eux-mêmes pour l'icône de l'onglet |
Brancher un relais ou une LED externe à la place
Une fois que tout marche avec la LED intégrée, piloter un vrai appareil depuis la même page ne demande de changer qu'une ligne : remplace Pin("LED", Pin.OUT) par exemple par Pin(16, Pin.OUT). Tu peux calculer la bonne résistance pour une LED externe avec l'outil Résistance de LED ; pour une broche en 3,3 V, 220 à 330 Ω suffisent. Avec un module relais, alimente le module par la broche VBUS en 5 V et relie son entrée IN au GPIO. Beaucoup de modules relais s'activent avec un signal LOW ; dans ce cas, inverse les lignes led.on() et led.off(). Les détails du câblage sont dans Qu'est-ce qu'un module relais ?.
| Composant | Broche du composant | Broche du Pico W (n° de broche physique) |
|---|---|---|
| LED externe | Anode (+), via une résistance de 220 Ω | GP14 (19) |
| LED externe | Cathode (−) | GND (18) |
| DHT22 | VCC / DATA / GND | 3V3(OUT) (36) / GP15 (20) / GND (38) |
| Module relais | VCC | VBUS, 5 V de l'USB (40) |
| Module relais | IN | GP16 (21) |
| Module relais | GND | GND (23) |
Étape 4 : afficher les données d'un capteur en direct sur une page web
La page de la LED se rechargeait entièrement à chaque appui sur un bouton. Sur une page qui affiche des mesures, c'est bien plus agréable quand les valeurs se mettent à jour sans rechargement. Pour cela, nous utiliserons deux chemins : / envoie la page elle-même et /data uniquement les mesures au format JSON. Un petit code JavaScript dans la page lit /data toutes les deux secondes et met les chiffres à jour. L'exemple affiche le capteur de température interne, qui ne demande aucun composant, et la puissance du signal Wi-Fi (RSSI) ; il construit aussi le serveur avec le module asyncio de MicroPython, pour que le Pico W continue à mesurer pendant qu'il attend les requêtes.
1import asyncio
2import json
3import time
4from machine import ADC, Pin
5import wifi
6
7wlan = wifi.connect()
8sensor = ADC(4) # dahili sıcaklık sensörü / internal temperature sensor
9led = Pin("LED", Pin.OUT)
10start = time.time()
11readings = {"temp": 0, "rssi": 0, "uptime": 0}
12
13HTML = """<!DOCTYPE html>
14<html><head><meta charset="utf-8">
15<meta name="viewport" content="width=device-width, initial-scale=1">
16<title>Pico W</title></head>
17<body style="font-family:sans-serif;text-align:center">
18<h1>Pico W</h1>
19<p>Sıcaklık / Temperature: <b id="t">-</b> °C</p>
20<p>Wi-Fi sinyali / signal: <b id="r">-</b> dBm</p>
21<p>Çalışma süresi / uptime: <b id="u">-</b> s</p>
22<script>
23async function update() {
24 try {
25 const d = await (await fetch("/data")).json();
26 document.getElementById("t").textContent = d.temp;
27 document.getElementById("r").textContent = d.rssi;
28 document.getElementById("u").textContent = d.uptime;
29 } catch (e) {}
30}
31update();
32setInterval(update, 2000);
33</script>
34</body></html>"""
35
36
37def read_temp():
38 volts = sensor.read_u16() * 3.3 / 65535
39 return round(27 - (volts - 0.706) / 0.001721, 1)
40
41
42async def measure():
43 while True:
44 readings["temp"] = read_temp()
45 readings["rssi"] = wlan.status("rssi") # yalnız STA modunda / STA mode only
46 readings["uptime"] = time.time() - start
47 led.toggle() # kalp atışı / heartbeat
48 await asyncio.sleep(2)
49
50
51async def handle(reader, writer):
52 try:
53 line = await reader.readline() # b"GET /data HTTP/1.1"
54 while True: # başlıkları atla / skip the headers
55 header = await reader.readline()
56 if header in (b"\r\n", b""):
57 break
58 parts = line.split(b" ")
59 path = parts[1] if len(parts) > 1 else b"/"
60 if path == b"/":
61 writer.write(b"HTTP/1.0 200 OK\r\nContent-Type: text/html; charset=utf-8\r\n\r\n")
62 writer.write(HTML.encode())
63 elif path == b"/data":
64 writer.write(b"HTTP/1.0 200 OK\r\nContent-Type: application/json\r\n\r\n")
65 writer.write(json.dumps(readings).encode())
66 else:
67 writer.write(b"HTTP/1.0 404 Not Found\r\n\r\n")
68 await writer.drain()
69 except OSError as e:
70 print("Bağlantı hatası / connection error:", e)
71 finally:
72 writer.close()
73 await writer.wait_closed()
74
75
76async def main():
77 await asyncio.start_server(handle, "0.0.0.0", 80)
78 print("Tarayıcıda aç / open in browser: http://" + wlan.ifconfig()[0])
79 await measure()
80
81
82asyncio.run(main())asyncio.start_server() lance la fonction handle comme une tâche séparée pour chaque nouvelle connexion du navigateur, tandis que la tâche measure() prend une mesure toutes les deux secondes en arrière-plan et fait clignoter la LED intégrée. Le clignotement te montre aussi que la carte n'est pas bloquée. Attention : avec asyncio, convertis le texte en octets avec .encode() avant de l'envoyer, sinon les pages contenant des accents provoqueront une erreur. Le capteur de température interne mesure la température de la puce elle-même : ses valeurs sont bruitées et décalées de quelques degrés par rapport à la pièce ; la formule 27 − (V − 0,706) / 0,001721 du code vient de la fiche technique du RP2040. Pour la vraie température ambiante, utilise un capteur externe.

Pour une vraie mesure de température et d'humidité, branche un DHT22 (DATA sur GP15). Le pilote des capteurs DHT est intégré au firmware du Pico W, tu n'as rien de plus à téléverser. Dans la fonction measure() du code du capteur, remplace la ligne readings["temp"] = read_temp() par un appel à read_sensor() ci-dessous, et ajoute une ligne pour l'humidité dans le HTML. Le DHT22 ne doit pas être lu plus d'une fois toutes les deux secondes, ce qui correspond justement au rythme de la boucle. Pour en savoir plus sur le capteur, lis Capteur de température et d'humidité DHT11.
1import dht
2from machine import Pin
3
4dht_sensor = dht.DHT22(Pin(15)) # DATA ucu GP15'te / DATA pin on GP15
5
6
7def read_sensor():
8 try:
9 dht_sensor.measure() # ölçümü başlat / trigger a reading
10 readings["temp"] = dht_sensor.temperature() # °C
11 readings["hum"] = dht_sensor.humidity() # % bağıl nem / % relative humidity
12 except OSError as e:
13 print("DHT22 okunamadı / read failed:", e)Étape 5 : appeler une API avec urequests (récupérer des données sur internet)
Le Pico W peut être client autant que serveur : il envoie une requête à un service en ligne et lit la réponse. Le module requests est intégré au firmware du Pico W ; le nom urequests des anciens exemples renvoie au même module, donc les deux écritures fonctionnent. L'exemple ci-dessous récupère la température, l'humidité et la vitesse du vent actuelles à Istanbul auprès du service météo gratuit Open-Meteo, qui ne demande aucune clé d'API. Il suffit de changer LAT et LON pour ta ville, par exemple 48.86 et 2.35 pour Paris.
1import requests
2import wifi
3
4wifi.connect()
5
6# İstanbul; kendi konumunu yaz / Istanbul; put your own location
7LAT, LON = 41.01, 28.98
8URL = ("https://api.open-meteo.com/v1/forecast?latitude={}&longitude={}"
9 "¤t=temperature_2m,relative_humidity_2m,wind_speed_10m").format(LAT, LON)
10
11response = requests.get(URL)
12try:
13 if response.status_code == 200:
14 current = response.json()["current"]
15 print("Sıcaklık / temperature:", current["temperature_2m"], "°C")
16 print("Nem / humidity:", current["relative_humidity_2m"], "%")
17 print("Rüzgâr / wind:", current["wind_speed_10m"], "km/h")
18 else:
19 print("HTTP hatası / HTTP error:", response.status_code)
20finally:
21 response.close() # soketi ve belleği serbest bırak / free the socket and memoryTrois points demandent ton attention dans ce code. D'abord, appelle response.close() après chaque réponse : les réponses non fermées consomment des sockets et de la mémoire, et après quelques requêtes tu tomberas sur « OSError: [Errno 12] ENOMEM ». Ensuite, response.json() charge toute la réponse en mémoire ; le Pico W n'a que 264 Ko de RAM au total, donc avec des API qui renvoient de gros JSON, utilise des adresses qui ne demandent que les champs utiles (comme le paramètre current ici). Enfin, une connexion HTTPS demande de la mémoire supplémentaire pour le chiffrement ; si tu envoies des requêtes régulières dans une boucle, ajouter gc.collect() entre elles réduit la fragmentation de la mémoire. Avec la même méthode, tu peux envoyer des messages Telegram, écrire des données dans un tableur ou récupérer des taux de change ; la création du bot Telegram est la même que dans Bot Telegram avec l'ESP32.
Étape 6 : l'heure exacte depuis internet avec NTP
Le Pico W possède une horloge temps réel (RTC) interne, mais sans pile de sauvegarde : à chaque mise sous tension, l'horloge revient au 1er janvier 2021. Une fois en Wi-Fi, obtenir l'heure exacte auprès des serveurs NTP d'internet est très simple : la fonction settime() du module intégré ntptime règle l'horloge interne en UTC. Pour l'heure locale, le code ajoute un décalage fixe ; l'exemple utilise 3 heures (10 800 secondes) pour la Turquie. En France, en Belgique et en Suisse, mets UTC_OFFSET à 1 * 3600 en hiver et à 2 * 3600 en été.
1import time
2import ntptime
3import wifi
4
5wifi.connect()
6ntptime.host = "pool.ntp.org" # varsayılan sunucu / default server
7UTC_OFFSET = 3 * 3600 # Türkiye UTC+3; kendi saat dilimini yaz / set your own time zone
8
9for attempt in range(5):
10 try:
11 ntptime.settime() # dahili saati UTC'ye ayarlar / sets the internal clock to UTC
12 print("Saat ayarlandı / time set")
13 break
14 except OSError as e:
15 print("NTP hatası / NTP error:", e)
16 time.sleep(2)
17
18DAYS = ("Pzt/Mon", "Sal/Tue", "Çar/Wed", "Per/Thu", "Cum/Fri", "Cmt/Sat", "Paz/Sun")
19
20while True:
21 y, mo, d, h, mi, s, wd, yd = time.localtime(time.time() + UTC_OFFSET)
22 print("%02d.%02d.%d %s %02d:%02d:%02d" % (d, mo, y, DAYS[wd], h, mi, s))
23 time.sleep(1)Par défaut, ntptime utilise le serveur pool.ntp.org et attend une seconde la réponse ; sans réponse, il lève « OSError: [Errno 110] ETIMEDOUT », c'est pourquoi le code fait cinq tentatives. L'horloge interne peut dériver de quelques secondes avec le temps : dans les projets qui tournent longtemps, rappelle settime() une fois par jour. Dans les pays à heure d'été, le décalage change deux fois par an ; tu devras le gérer dans le code avec un test sur la date. Pour afficher l'heure sur un écran, combine ce code avec les exemples MicroPython des articles sur l'écran OLED ou l'écran LCD I2C ; la version ESP32 se trouve dans ESP32 NTP.
Créer ton propre réseau (mode AP) et l'adresse picow.local
Là où il n'y a pas de box, par exemple sur un stand de fête de la science ou au jardin, le Pico W peut diffuser son propre réseau Wi-Fi. En mode point d'accès, tu connectes ton téléphone directement au réseau « PicoW-BlueGrays » et tu ouvres la page à l'adresse http://192.168.4.1. Le code du serveur web fonctionne sans modification ; écris simplement les lignes ci-dessous à la place de wlan = wifi.connect() et ajoute wlan = ap. Le mot de passe doit comporter au moins 8 caractères. La ligne RSSI de l'exemple du capteur ne fonctionne qu'en mode station, supprime-la en mode AP. Dans ce mode, le Pico W n'a pas accès à internet : les exemples NTP et API ne fonctionnent donc pas.
1import network
2
3ap = network.WLAN(network.WLAN.IF_AP)
4ap.config(ssid="PicoW-BlueGrays", password="bluegrays123") # şifre en az 8 karakter / at least 8 characters
5ap.active(True)
6while not ap.active():
7 pass
8print("Ağ hazır / network ready:", ap.ifconfig()[0]) # genellikle 192.168.4.1 / usually 192.168.4.1S'il est fastidieux de relire l'adresse IP dans le Shell à chaque fois, tu peux utiliser un nom. Les versions récentes de MicroPython prennent en charge le mDNS sur le Pico W : grâce à la ligne network.hostname("picow") de wifi.py, la carte répond aussi à l'adresse http://picow.local. Cette adresse fonctionne généralement sous Windows, macOS, Linux et sur iPhone ; certains téléphones Android n'ouvrent pas les adresses .local, utilise alors l'adresse IP. Si tu veux que l'adresse IP ne change jamais, le plus fiable est d'attribuer une IP fixe à l'adresse MAC du Pico W dans l'interface de ta box (bail DHCP statique).
Note sur le Pico 2 W : qu'est-ce qui change ?
Le Pico 2 W a la même taille et le même brochage que le Pico W et utilise la même puce sans fil CYW43439 ; seul son processeur change, avec le RP2350, plus rapide. Côté logiciel, la seule différence est le firmware : télécharge le fichier RPI_PICO2_W sur micropython.org ; en mode BOOTSEL, le lecteur apparaît sous le nom RP2350. Tout le code MicroPython de cet article fonctionne sans modification. Avec 520 Ko de RAM, les requêtes HTTPS, les grosses réponses JSON et les longues pages HTML tiennent beaucoup plus à l'aise sur le Pico 2 W. Dans l'Arduino IDE, choisis la carte Raspberry Pi Pico 2W. Une remarque : les premières versions du RP2350 présentent un erratum connu (E9) qui touche les résistances de pull-down internes ; pour les boutons, les relier à GND et utiliser PULL_UP reste la solution la plus sûre. Pour les fonctions avancées comme les deux cœurs et le PIO, lis PIO et double cœur du Pico.
Alternative : programmer le Pico W avec l'Arduino IDE (arduino-pico)
Si le C++ et les bibliothèques Arduino te sont plus familiers, tu peux programmer le Pico W depuis l'Arduino IDE avec le core arduino-pico d'Earle Philhower. Il fournit des bibliothèques WiFi et WebServer compatibles avec celles de l'ESP32 : un code de serveur web écrit pour l'ESP32 fonctionne donc sur le Pico W avec de petites modifications.
- Dans l'Arduino IDE, ouvre Fichier > Préférences et ajoute https://github.com/earlephilhower/arduino-pico/releases/download/global/package_rp2040_index.json dans le champ « URL de gestionnaire de cartes supplémentaires ».
- Dans le gestionnaire de cartes, cherche pico et installe le paquet Raspberry Pi Pico/RP2040/RP2350 d'Earle F. Philhower.
- Choisis Raspberry Pi Pico W dans Outils > Type de carte (Raspberry Pi Pico 2W pour le Pico 2 W).
- Pour le premier téléversement, branche la carte en maintenant BOOTSEL enfoncé ; l'Arduino IDE la détecte comme lecteur UF2. Pour les téléversements suivants, il suffit de choisir le port série qui apparaît dans Outils > Port.
- Après le téléversement, ouvre le moniteur série à 115200 bauds et lis l'adresse IP.
1#include <WiFi.h>
2#include <WebServer.h>
3#include <LEAmDNS.h>
4
5const char* ssid = "AgAdi"; // Wi-Fi adın / your Wi-Fi name
6const char* password = "Sifre123"; // Wi-Fi şifren / your Wi-Fi password
7
8WebServer server(80);
9bool ledOn = false;
10
11void sendPage() {
12 String html = "<!DOCTYPE html><html><head><meta charset='utf-8'>"
13 "<meta name='viewport' content='width=device-width, initial-scale=1'>"
14 "<title>Pico W</title></head>"
15 "<body style='font-family:sans-serif;text-align:center'><h1>Pico W LED</h1>";
16 html += "<p>Durum / State: <b>";
17 html += ledOn ? "AÇIK / ON" : "KAPALI / OFF";
18 html += "</b></p><p><a href='/on'><button>AÇ / ON</button></a> ";
19 html += "<a href='/off'><button>KAPAT / OFF</button></a></p>";
20 html += "<p>Sıcaklık / Temp: ";
21 html += String(analogReadTemp(), 1); // dahili sensör / internal sensor
22 html += " °C</p></body></html>";
23 server.send(200, "text/html", html);
24}
25
26void setup() {
27 Serial.begin(115200);
28 pinMode(LED_BUILTIN, OUTPUT); // Pico W'de kablosuz yongadaki LED / the LED on the wireless chip
29 WiFi.mode(WIFI_STA);
30 WiFi.begin(ssid, password);
31 while (WiFi.status() != WL_CONNECTED) {
32 delay(500);
33 Serial.print(".");
34 }
35 Serial.println();
36 Serial.print("IP: ");
37 Serial.println(WiFi.localIP()); // bu adresi telefonda aç / open this address on your phone
38
39 MDNS.begin("picow"); // http://picow.local
40 server.on("/", sendPage);
41 server.on("/on", []() { ledOn = true; digitalWrite(LED_BUILTIN, HIGH); sendPage(); });
42 server.on("/off", []() { ledOn = false; digitalWrite(LED_BUILTIN, LOW); sendPage(); });
43 server.onNotFound([]() { server.send(404, "text/plain", "404"); });
44 server.begin();
45}
46
47void loop() {
48 server.handleClient();
49 MDNS.update();
50}Ce croquis fait la même chose que la page LED en MicroPython et ajoute la température interne lue avec analogReadTemp(). Sur le Pico W, LED_BUILTIN pilote automatiquement la LED reliée à la puce sans fil, et la ligne MDNS.begin("picow") rend la page accessible aussi à l'adresse http://picow.local. Le pilote Wi-Fi ajoute environ 220 Ko au programme compilé, la première compilation peut donc prendre un moment. Pour choisir entre MicroPython et Arduino, garde ceci en tête : avec MicroPython, tu enregistres le code et tu l'essaies immédiatement ; avec Arduino, tu attends la compilation, mais tu obtiens un code plus rapide et un large choix de bibliothèques.
Idées de projets avec le Raspberry Pi Pico W
- Thermomètre Wi-Fi : suis depuis ton téléphone la température et l'humidité mesurées par un DHT11 ou un DHT22.
- Lampe pilotée par téléphone : ajoute un module relais à la page LED de cet article et allume ou éteins ta lampe de bureau.
- Suivi de l'humidité des plantes : affiche la valeur du capteur d'humidité du sol sur la page et préviens-toi quand la terre sèche.
- Alerte de mouvement : quand un capteur PIR détecte quelqu'un, envoie un message Telegram sur ton téléphone avec urequests.
- Horloge internet : affiche l'heure NTP avec la date et le jour de la semaine sur un écran OLED.
- Domotique : installe la bibliothèque umqtt.simple avec mip et envoie tes mesures à Home Assistant via MQTT ; le principe est expliqué dans ESP32 MQTT.
- Tableau de bord en temps réel : pour des pages qui se mettent à jour plus vite, adapte au Pico W les idées de l'article serveur web asynchrone ESP32, basé sur WebSocket.
Erreurs fréquentes et solutions
| Symptôme ou erreur | Cause | Solution |
|---|---|---|
| ImportError: no module named 'network' | Firmware du Pico classique flashé sur le Pico W | Flashe l'UF2 RPI_PICO_W (RPI_PICO2_W pour le Pico 2 W) |
| wlan.status() reste à -2 | Réseau invisible : 5 GHz, mauvais nom de réseau ou signal faible | Active la bande 2,4 GHz, cherche le réseau avec wlan.scan(), rapproche la carte de la box |
| wlan.status() renvoie -3 | Mauvais mot de passe | Ressaisis-le en respectant majuscules, minuscules et espaces |
| OSError: [Errno 98] EADDRINUSE | Le socket du serveur précédent occupe encore le port 80 | Utilise SO_REUSEADDR, redémarre avec Ctrl+D |
| La page ne s'ouvre pas sur le téléphone | Le téléphone est en données mobiles, sur le réseau invité, ou l'isolation des clients est activée sur la box | Connecte le téléphone au même Wi-Fi et tape l'adresse en http, pas en https |
| OSError: -2 (urequests) | Nom d'hôte impossible à résoudre : pas de Wi-Fi ou problème DNS | Appelle d'abord wifi.connect() et vérifie l'URL |
| OSError: [Errno 12] ENOMEM | Mémoire pleine | Utilise response.close() et gc.collect(), demande des réponses plus petites |
| La connexion tombe au bout de quelques heures | Économie d'énergie ou redémarrage de la box | Utilise pm=network.WLAN.PM_NONE, vérifie wlan.isconnected() dans la boucle et reconnecte-toi |
| Ne fonctionne plus une fois débranché de l'ordinateur | Le code n'est pas enregistré sous main.py ou wifi.py manque sur le Pico | Enregistre les deux fichiers sur le Pico |
Comme tu l'as vu, connecter le Raspberry Pi Pico W au Wi-Fi, servir une page web et récupérer des données sur internet tient en quelques fichiers : wifi.py gère la connexion et main.py le projet lui-même. Pour consolider tes bases sur le Pico, l'application BlueGrays propose des projets Raspberry Pi Pico avec des LED, un feu tricolore, du PWM et une LED RGB, et côté ESP32 des projets de connexion Wi-Fi, de serveur web asynchrone, d'horloge NTP et d'API météo, chacun avec schéma de câblage et code pas à pas.
Questions fréquentes
Le Raspberry Pi Pico W se connecte-t-il au Wi-Fi 5 GHz ?
Non. La puce CYW43439 du Pico W et du Pico 2 W ne fonctionne que dans la bande 2,4 GHz et ne voit pas les réseaux 5 GHz. Vérifie que la bande 2,4 GHz de ta box est activée ; si les deux bandes portent le même nom et que tu as des soucis, donner un nom distinct au 2,4 GHz règle souvent le problème.
Comment installer MicroPython sur le Pico W ?
Télécharge sur micropython.org le fichier .uf2 de la carte RPI_PICO_W. Maintiens le bouton BOOTSEL enfoncé en branchant le Pico W à l'ordinateur, puis glisse le fichier sur le lecteur RPI-RP2 qui apparaît. La carte redémarre et elle est prête à l'emploi avec Thonny ; la fenêtre « Install or update MicroPython » de Thonny fait la même chose.
Comment trouver l'adresse IP du Pico W ?
Une fois connecté, wlan.ifconfig()[0] donne l'adresse IP, et le fichier wifi.py de cet article l'affiche dans le Shell. Si la carte n'est pas reliée à un ordinateur, consulte la liste des appareils connectés dans l'interface de ta box ou essaie http://picow.local sur un appareil compatible mDNS.
Pourquoi la LED intégrée du Pico W ne s'allume-t-elle pas avec Pin(25) ?
Sur le Pico W, la LED intégrée est reliée à la puce sans fil et non au processeur, et GP25 sert de ligne de sélection de cette puce. Avec Pin("LED", Pin.OUT) en MicroPython ou LED_BUILTIN dans l'Arduino IDE, la LED s'allume correctement. Cette écriture fonctionne aussi sur le Pico classique, tu peux donc toujours l'utiliser.
Puis-je accéder au serveur web du Pico W depuis internet ?
Techniquement oui, en ouvrant des ports sur ta box, mais ce n'est pas recommandé : un serveur MicroPython simple n'a ni chiffrement ni authentification. Pour un pilotage à distance, un intermédiaire comme MQTT, un bot Telegram ou un service IoT dans le cloud est bien plus sûr.
Pico W ou ESP32 : lequel choisir pour un projet Wi-Fi ?
Les deux offrent le Wi-Fi 2,4 GHz et le Bluetooth. Si tu veux travailler en MicroPython avec une documentation claire et des broches sans surprise, choisis le Pico W ; si tu as besoin de plus de vitesse, de nombreuses entrées analogiques et d'un vaste choix de bibliothèques Arduino, l'ESP32 convient mieux. Pour un simple serveur web, des capteurs ou des appels d'API, les deux font très bien l'affaire.
Projets à réaliser après cet article
Voir tous les projets
Clignotement LED Intégrée Raspberry Pi Pico (Pico et Pico W)
Le projet d'ouverture de la série Raspberry Pi Pico ! Nous faisons clignoter la LED verte intégrée pour vérifier que la carte fonctionne — une première expérience classique "Hello World". AUCUN composant externe, juste Pico et câble USB. Le code est écrit en MicroPython (le langage officiellement soutenu par la Raspberry Pi Foundation). Apprends la classe machine.Pin, le mode Pin.OUT, les méthodes led.on()/off() et time.sleep() dans Thonny IDE. Suis chaque basc

Allumage d'une LED externe sur le Raspberry Pi Pico (plaque d'essai)
Après la LED intégrée du Pico : connecter une LED externe à la maquette et la contrôler via la broche GP14. Ce projet vous permet d’apprendre comment utiliser n’importe quelle broche GPIO à usage général du Pico en sortie, de comprendre la polarité de la LED (grande patte = anode/+, petite patte = cathode/–) et de découvrir pourquoi une résistance de limitation de courant (220 Ω) est indispensable. Si vous n'installez pas cette résistance, un courant excessif traversera la LED et celle-ci risque

Simulateur de Feu de Circulation Raspberry Pi Pico (3 LEDs séquentielles)
Nous simulons un vrai feu de circulation avec des LEDs rouge, jaune et verte. Vert 4 sec "passez", jaune 1,5 sec "préparez", rouge 3 sec "arrêtez" et rouge+jaune 1 sec "départ" (motif européen). Apprends la définition de fonction, la logique de machine à états et la synchronisation multi-GPIO. Circuit simple : 3 LEDs sur GP11/GP12/GP13, chacune avec 220Ω.

Raspberry Pi Pico PWM LED Fade (Effet Respiration)
La LED ne clignote plus — elle respire ! Grâce au PWM (modulation de largeur d'impulsion) du Raspberry Pi Pico, la luminosité monte puis descend lentement. Apprends la classe machine.PWM, duty_u16() (luminosité 16 bits 0–65535), la fréquence PWM, les boucles range() et la sortie quasi analogique. Base du mélange de couleurs RGB, du contrôle moteur, des servos et du buzzer.

Serveur Web asynchrone ESP32 (avec affichage de l'adresse IP sur l'écran LCD)
Dans ce projet, nous transformons l'ESP32 en un serveur web asynchrone que vous pouvez contrôler depuis votre téléphone ou votre ordinateur connecté au même réseau Wi-Fi. Grâce à la bibliothèque ESPAsyncWebServer, le serveur peut traiter plusieurs requêtes simultanément (contrairement au classique WebServer.h qui se bloque sur une seule requête). Depuis votre navigateur, vous pourrez vous connecter à l'adresse IP de l'ESP32, puis allumer et éteindre la LED co

Connexion Wi-Fi STA ESP32 (avec écran LCD)
Dans ce projet, nous connectons l'ESP32 au réseau Wi-Fi domestique en mode Station (STA) de manière sécurisée et tolérante aux pannes. Nous isolons SSID/mot de passe dans un fichier secrets.h pour empêcher leur fuite sur Git, mettons en place une reconnexion automatique, et affichons le niveau RSSI et l'adresse IP sur un écran LCD I2C. La LED intégrée sert d'indicateur d'état.

ESP32 : heure réelle depuis Internet via NTP
L'ESP32 se connecte au Wi-Fi et récupère l'heure réelle avec une précision de la milliseconde depuis des serveurs NTP (Network Time Protocol). Grâce à configTzTime(), le fuseau horaire de la Turquie (TRT, UTC+3) est appliqué automatiquement et le passage DST est géré via la chaîne POSIX TZ. L'heure est affichée sur le moniteur série et sur un écran LCD I2C en option. configTzTime() démarre le service SNTP ; des resynchronisations périodiques ont lieu tant que l'accès au réseau est disponible

ESP32 HTTPClient + API météo (avec écran LCD)
Dans ce projet, nous effectuons un appel REST à l'API météo (wttr.in) via Internet à l'aide de l'ESP32 et de la bibliothèque HTTPClient.h. À l’aide d’ArduinoJson v7, nous analysons la réponse JSON renvoyée et affichons les informations relatives à la ville, à la température, à l’humidité, à la météo et au vent sur un écran LCD I2C, en turc et en anglais. wttr.in est gratuit et ne nécessite pas de clé API : il suffit de saisir le nom d’une ville pour obtenir les conditions météo en temps réel d
Autres articles
Application BlueGrays
Réalise ce montage pas à pas sur ton téléphone
Schéma, code et liste des composants sur un seul écran. Plus de 200 projets Arduino, ESP32 et Pico à réaliser.
Scanne avec ton téléphone
Pointe l’appareil photo vers le code : la boutique d’applications de ton téléphone s’ouvre.
ou ouvre la boutique

