try:
import usocket as socket
except:
import socket
import network
from time import sleep
import ubinascii
from micropython import const
HEADER = "F" * 12
LED = machine.Pin(0, machine.Pin.OUT)
LED.value(0)
def create_magic_packet(macaddress: str) -> bytes:
if len(macaddress) == 17:
sep = macaddress[2]
macaddress = macaddress.replace(sep, "")
elif len(macaddress) != 12:
raise ValueError("Incorrect MAC address format")
return ubinascii.unhexlify(HEADER + macaddress * 16)
def send_magic_packet(
*macs: str,
ip_address: str,
port: int = 9,
interface: str = None
) -> None:
packets = [create_magic_packet(mac) for mac in macs]
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
if interface is not None:
sock.bind((interface, 0))
sock.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)
sock.connect((ip_address, port))
for packet in packets:
sock.send(packet)
sock.close()
_hexdig = '0123456789ABCDEFabcdef'
_hextobyte = None
def unquote(string):
"""unquote('abc%20def') -> b'abc def'."""
global _hextobyte
# Note: strings are encoded as UTF-8. This is only an issue if it contains
# unescaped non-ASCII characters, which URIs should not.
if not string:
return b''
if isinstance(string, str):
string = string.encode('utf-8')
bits = string.split(b'%')
if len(bits) == 1:
return string
res = [bits[0]]
append = res.append
# Delay the initialization of the table to not waste memory
# if the function is never called
if _hextobyte is None:
_hextobyte = {(a + b).encode(): bytes([int(a + b, 16)])
for a in _hexdig for b in _hexdig}
for item in bits[1:]:
try:
append(_hextobyte[item[:2]])
append(item[2:])
except KeyError:
append(b'%')
append(item)
return b''.join(res)
def start_access_point():
global ap
ssid = 'POWA-AP'
password = '123454321'
ap = network.WLAN(network.AP_IF)
ap.active(True)
ap.config(essid=ssid, password=password)
while ap.active() == False:
pass
print('AP start successful')
print(ap.ifconfig())
def stop_access_point():
if ('ap' in globals()):
ap.active(False)
def stop_socket_loop():
if ('conn' in globals()):
conn.close()
def parse_params(part):
parameters = {}
for piece in part.split(" "):
if "/?" in piece:
piece = piece.replace("/?", "")
amp_split = piece.split("&")
for param_set in amp_split:
eq_split = param_set.split("=")
parameters[eq_split[0]] = eq_split[1]
return parameters
def send_config_page():
f = open('index.html', 'r')
while True:
chunk = f.read(5024)
if not chunk:
break
conn.sendall(str(chunk))
conn.close()
f.close()
def web_page_success():
html = """<html><body><h1 style="color:green; position: absolute; top: 50%; left: 45%; width:10%">SUCCESS</h1></body></html>"""
return html
def do_connect():
global sta_if
sta_if = network.WLAN(network.STA_IF)
if not sta_if.isconnected():
print('connecting to network...')
try:
fssid = open('ssid.dat')
fpass = open('password.dat')
except OSError:
print('Open files error')
fssid = ""
fpass = ""
sta_if = network.WLAN(network.STA_IF)
sta_if.active(True)
sta_if.connect(fssid.readline(), fpass.readline())
while not sta_if.isconnected():
pass
print('network config:', sta_if.ifconfig())
a = sta_if.config('mac')
print('MAC {:02x}:{:02x}:{:02x}:{:02x}:{:02x}'.format(a[0],a[1],a[2],a[3],a[4]))
def boot():
try:
fmac = open('mac.dat')
mac = fmac.readline()
mask = sta_if.ifconfig()[1].split('.')[3]
if(mask == '255'):
mask = '0'
else:
mask = '255'
ip = sta_if.ifconfig()[2].split('.')
ip_broadcast = ip[0] + '.' + ip[1] + '.' + ip[2] + '.' + mask
print('Broadcast ip is ' + ip_broadcast)
except OSError:
print('Open files error')
send_magic_packet(str(mac), ip_address = str(ip_broadcast))
sleep(0.5)
print('Magic packet sent for ' + mac)
def stop_wifi():
if('sta_if' in globals):
sta_if.active(False)
def start_socket_loop():
gc.collect()
addr = socket.getaddrinfo('0.0.0.0', 80)[0][-1]
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
s.setblocking(False)
s.bind((addr))
s.listen()
s.settimeout(None)
while True:
global conn
conn, addr = s.accept()
print('Got a connection from %s' % str(addr))
request = conn.recv(4096)
print('Content = %s' % str(request))
params = parse_params(str(request))
if(params.get('mac') is not None and params.get('ssid') is not None and params.get('password') is not None):
#get ssid/password Home wifi drom the android browser
sta_if = network.WLAN(network.STA_IF)
sta_if.active(True)
sta_if.connect(params.get('ssid'), params.get('password'))
while not sta_if.isconnected():
pass
if(sta_if.isconnected()):
f = open('mac.dat', 'w')
f.write(unquote(str(params.get('mac'))))
f.close()
f = open('ssid.dat', 'w')
f.write(unquote(str(params.get('ssid'))))
f.close()
f = open('password.dat', 'w')
f.write(unquote(str(params.get('password'))))
f.close()
response = web_page_success()
conn.send('HTTP/1.1 200 OK\n')
conn.send('Content-Type: text/html\n')
conn.send('Connection: close\n\n')
conn.sendall(str(response))
break
else:
send_config_page()
else:
send_config_page()
gc.collect()
sleep(0.5)
gc.collect()
sleep(0.5)
#app
do_connect()
if machine.reset_cause() == machine.DEEPSLEEP_RESET:
print('woke from a deep sleep')
if(sta_if.isconnected()):
print('Connected to home wifi')
boot()
stop_socket_loop()
stop_access_point()
print('Turn to deep sleep')
machine.deepsleep()
else:
start_access_point()
start_socket_loop()
else:
print('power on or hard reset')
if(sta_if.isconnected()):
print('Connected to home wifi')
boot()
stop_socket_loop()
stop_access_point()
print('Turn to deep sleep')
machine.deepsleep()
else:
start_access_point()
start_socket_loop()
Créer un bouton sans fil sous esp8266 (01/01s) pour démarrer son PC (magic packet)
#main.py Projet à télécharger ici https://monkeytime.be/blog/data/medias/powa.zip
Je l'ai créer avec ce type de bouton acheté sur Amazon en lui adaptant un petit boitier pour contenir l'électronique et ce petit bouton power.