Pi Pico Webserver with ESP01 using AT Command

Firstly pressed on jalanjalantok.wordpress.com

To make this, you need an ESP-01 wifi module and make little setup. Please refer to my previous post about adding wireless capability to Pi Pico Part 2.

Pi Pico relies on ESP-01 on processing AT command to receive request from a web browser and send message to the browser.

Pico is responsible to send AT command via UART to ESP-01. And Pico reads all returning message via UART from ESP-01 process it and send respond to ESP-01 via UART.

Here is output from two-ways communication between Pi Pico and ESP-01 to publish data to web browser using AT command that you may analyze.

UART(0, baudrate=9600, bits=8, parity=None, stop=1, tx=16, rx=17, timeout=0, timeout_char=2, invert=None)
CMD: AT

b'AT\r\r\n\r\nOK\r\n'
CMD: AT+GMR

b'AT+GMR\r\r\nAT version:1.2.0.0(Jul  1 2016 20:04:45)\r\nSDK version:1.5.4.1(39cb9a32)\r\nv1.0.0\r\nMar 11 2018 18:27:31\r\nOK\r\n'
CMD: AT+RST

b'AT+RST\r\r\n\r\nOK\r\nWIFI DISCONNECT\r\nF!\xdc\x8d\x10\xa4<11\x95\x86q))\x81\x18\x9cv1\xcc\xd1\xec\xc0\xcc 1\xbd1\x84\xe1\xd9iii\xa2\xd8FT@I\xf6\xd8I\xfc\r\nready\r\n'
CMD: AT+CWMODE=3

b'AT+CWMODE=3\r\r\n\r\nOK\r\nWIFI CONNECTED\r\n'
CMD: AT+CWJAP="MySSID","MyPassword"

b'AT+CWJAP="MySSID","MyPassword"\r\r\nWIFI DISCONNECT\r\nWIFI CONNECTED\r\n'
>>> setupServer()
CMD: AT+CIPSTATUS

b'WIFI GOT IP\r\n\r\nOK\r\nAT+CIPSTATUS\r\r\nSTATUS:2\r\n\r\nOK\r\n'
CMD: AT+CIPMUX=1

b'AT+CIPMUX=1\r\r\n\r\nOK\r\n'
>>> main()
CMD: AT+CIPSERVER=1,80

b'AT+CIPSERVER=1,80\r\r\n\r\nOK\r\n'
b'0,CONNECT\r\n1,CONNECT\r\n\r\n+IPD,0,473:GET / HTTP/1.1\r\nHost: 192.168.43.123\r\nConnection: keep-alive\r\nCache-Control: max-age=0\r\nUpgrade-Insecure-Requests: 1\r\nUser-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.114 Safari/537.36 Edg/89.0.774.75\r\nAccept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9\r\nAccept-Encoding: gzip, deflate\r\nAccept-Language: en-US,en;q=0.9,id;q=0.8\r\n\r\n'
CMD: AT+CIPSEND=0,15

b'AT+CIPSEND=0,15\r\r\n\r\nOK\r\n> 1,CLOSED\r\n'
CMD: Temperature: 22

b'\r\r\nbusy s...\r\n\r\nRecv 15 bytes\r\n\r\nSEND OK\r\n'
CMD: AT+CIPCLOSE=0

b'AT+CIPCLOSE=0\r\r\n0,CLOSED\r\n\r\nOK\r\n0,CONNECT\r\n\r\n+IPD,0,433:GET /favicon.ico HTTP/1.1\r\nHost: 192.168.43.123\r\nConnection: keep-alive\r\nPragma: no-cache\r\nCache-Control: no-cache\r\nUser-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/89.0.4389.114 Safari/537.36 Edg/89.0.774.75\r\nAccept: image/webp,image/apng,image/svg+xml,image/*,*/*;q=0.8\r\nReferer: http://192.168.43.123/\r\nAccept-Encoding: gzip, deflate\r\nAccept-Language: en-US,en;q=0.9,id;q=0.8\r\n\r\n'
CMD: AT+CIPSERVER=0

b'AT+CIPSERVER=0\r\r\n\r\nOK\r\n0,CLOSED\r\n'

Line 28 is the request from the web browser and the following line 29 is respond back from ESP-01 to tell the length of message to send. Finally line 32 is the actual message.

Line 35 and 38 will ensure that the message is displayed on the web browser as you can see below.

This is far from perfect and here is the code for you to try:

from machine import Pin, UART
import time
import urandom

uart=UART(0,9600, tx=Pin(16), rx=Pin(17))
print(uart)

ssid="MySSID"
psk="MyPassword"

def send(cmd, timeout=2000):
    print("CMD: " + cmd)
    uart.write(cmd.encode('utf-8'))
    wait(timeout)
    
def wait(timeout=2000):
    t0 = time.ticks_ms()
    resp = b""
    while (time.ticks_ms()-t0) < timeout:
        if uart.any():
            resp = b"". join([resp, uart.read(1)])
    #print(resp.decode('utf-8'))
    print(resp)
    return resp

def initiate():
    send("AT\r\n")
    send("AT+GMR\r\n")
    send("AT+RST\r\n")
    send("AT+CWMODE=3\r\n")
    
def connect(ssid,psk):
    send('AT+CWJAP="{}","{}"\r\n'.format(ssid,psk), 5000)

def ifconfig():
    send("AT+CIFSR\r\n", 5000)
   
def setupServer():
    send("AT+CIPSTATUS\r\n")
    send("AT+CIPMUX=1\r\n")

def main():
    send("AT+CIPSERVER=1,80\r\n")
    client_id=wait(5000)
    if len(client_id) >0:
        client_id=int(client_id.decode('utf-8')[client_id.decode('utf-8').find('+IPD')+5:client_id.decode('utf-8').find('+IPD')+6])
    temp=urandom.randrange(20,30)
    send("AT+CIPSEND={},{}\r\n".format(client_id,15))
    send("Temperature: {}\r\n".format(temp))
    send("AT+CIPCLOSE=0\r\n")
    send("AT+CIPSERVER=0\r\n")
        
if __name__ == '__main__':
    initiate()
    connect(ssid,psk)

Hope you find this post useful for your experiment. Thanks for reading and until next post.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google photo

You are commenting using your Google account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s