# micropython-wifimanager
A simple network configuration utility for MicroPython on boards such as ESP8266 and ESP32.
#### Test Start
Upload wifi_manager.py and your networks.json, then in the REPL:
```python
# simple_test.py — copy to board and run in REPL
from wifi_manager import WifiManager
# this should synchronously connect to your first known network
# and return True/False immediately
ok = WifiManager.setup_network()
print("✅ network OK" if ok else "❌ network failed")
```
#### Production Usage
##### a) Asynchronous, managed in background
Create main.py on your device:
```python
import uasyncio as asyncio
import logging
from wifi_manager import WifiManager
logging.basicConfig(level=logging.INFO)
WifiManager.on_connection_change(lambda evt, **kw: print("Event:", evt, kw))
# start the periodic manager
WifiManager.start_managing()
# hand off to uasyncio
asyncio.get_event_loop().run_forever()
```
> **Note:** scans and auto-reconnects every 10 s per your config.
##### b) Auto-start on boot
###### 1. `boot.py` (runs at power-on, no REPL)
```python
# boot.py
import machine, os
# mount filesystem, etc.
# then launch main.py automatically
try:
import main
except Exception as e:
# fail-safe: at least bring up AP
from wifi_manager import WifiManager
WifiManager.setup_network()
```
###### 2. `main.py` (as above)
With that in place, on every reset your board will:
• Run boot.py
• Hand off to your async manager in main.py,
• Bring up either your known STA networks or fallback AP + WebREPL.
#### Configuration
Simply upload your JSON file with your networks, the default path is '/networks.json', which is specified in the class property `config_file`.
A sample configuration may look like this:
{
"schema": 2,
"known_networks": [
{
"ssid": "User\u2019s iPhone",
"password": "Password1",
"enables_webrepl": false
},
{
"ssid": "HomeNetwork",
"password": "Password2",
"enables_webrepl": true
}
],
"access_point": {
"config": {
"essid": "Micropython-Dev",
"channel": 11,
"hidden": false,
"password": "P@55W0rd"
},
"enables_webrepl": true,
"start_policy": "fallback"
},
"config_server": {
"enabled": false,
"password": "micropython"
}
}
#### Configuration schema
* **schema**: currently this should be `2`
* **known_networks**: list of networks to connect to, in order of most preferred first
* SSID - the name of the access point
* password - the clear-text password to use
* enables_webrepl - a boolean value to indicate if connection to this network desires webrepl being started
* **access_point**: the details for the access point (AP) of this device
* config - the keys for the AP config, exactly as per the micropython documentation
* enables_webrepl - a boolean value to indicate if ceating this network desires webrepl being started
* start_policy - A policy from the below list to indicate when to enable the AP
* 'always' - regardless of the connection to any base station, AP will be started
* 'fallback' - the AP will only be started if no network could be connected to
* 'never' - The AP will not be started under any condition
* **config_server**: optional web configuration interface settings
* enabled - boolean to enable/disable the web config interface
* password - password for HTTP Basic Authentication (username is "admin")
#### Simple usage (one shot)
Here's an example of how to use the WifiManager.
MicroPython v1.9.4 on 2018-05-11; ESP32 module with ESP32
Type "help()" for more information.
>>> from wifi_manager import WifiManager
>>> WifiManager.setup_network()
connecting to network Foo-Network...
WebREPL daemon started on ws://10.1.1.234:8266
Started webrepl in normal mode
True
#### Asynchronous usage (event loop)
The WifiManager can be run asynchronously, via the cooperative scheduling that micropthon has in uasyncio. If you call `WifiManager.start_managing()` as follows, it will ensure that periodically the network status is scanned, and connection will be re-established as per preferences as needed.
import uasyncio as asyncio
import logging
from wifi_manager import WifiManager
logging.basicConfig(level=logging.WARNING)
WifiManager.start_managing()
asyncio.get_event_loop().run_forever()
#### Web configuration interface
For easier configuration management, WifiManager includes an optional web interface that allows you to view and edit the configuration remotely through a browser.
**Enable in configuration:**
```json
{
"schema": 2,
"known_networks": [...],
"access_point": {...},
"config_server": {
"enabled": true,
"password": "your-password-here"
}
}
```
**Manual start:**
```python
from wifi_manager import WifiManager
WifiManager.start_config_server("your-password")
```
**Usage:**
1. Connect to your device's network (either managed network or AP)
2. Open browser to `http://[device-ip]:8080`
3. Enter username "admin" and your configured password
4. Edit JSON configuration in the web interface
5. Click "Save & Apply" to update and restart networking
**Features:**
- Live JSON validation
- Automatic network restart after changes
- HTTP Basic Authentication protection
- Works with any modern browser
- Integrated with async event loop
#### Connection state callbacks
WifiManager can notify your application when the WiFi connection state changes, allowing you to respond to connectivity events in real-time.
**Register a callback:**
```python
def my_connection_handler(event, **kwargs):
if event == 'connected':
print(f"Connected to {kwargs.get('ssid')} with IP {kwargs.get('ip')}")
# Turn on LED, start data collection, etc.
elif event == 'disconnected':
print("Lost WiFi connection")
# Turn off LED, pause operations, etc.
elif event == 'ap_started':
print(f"Started access point: {kwargs.get('essid')}")
# Different LED color for AP mode
elif event == 'connection_failed':
print(f"Failed to connect to: {kwargs.get('attempted_networks')}")
# Log failure, try alternative approach
from wifi_manager import WifiManager
WifiManager.on_connection_change(my_connection_handler)
WifiManager.start_managing()
```
**Available events:**
- `connected` - Successfully connected to a network (includes `ssid` and `ip`)
- `disconnected` - Lost connection to network
- `ap_started` - Access point was activated (includes `essid`)
- `connection_failed` - All connection attempts failed (includes `attempted_networks`)
**Features:**
- Multiple callbacks supported
- Automatic state change detection
- Exception handling in callbacks won't crash the manager
- Callbacks can be added/removed dynamically
#### Contribution
Found a bug, or want a feature? open an issue.
If you want to contribute, create a pull request.
#### System flow
```mermaid
graph TD
A[Asynchronous Entry] -- start_managing --> B[Event Loop]
C[Synchronous Entry] -- setup_network --> D[Load Config File]
B -- manage --> E[Check Connection Status]
E -- connected --> F[Sleep 10s]
E -- disconnected --> D
D -- success --> G[Activate WLAN]
D -- file error --> D1[Use Default Config]
D1 --> G
G --> H[Scan Available Networks]
H -- scan success --> I[Match & Rank Candidates]
H -- scan error --> M[Configure AP]
I --> J[Try Next Candidate]
J -- has candidate --> K[Attempt Connection]
J -- no candidates --> M
K -- connected --> M
K -- failed --> J
M[Configure Access Point] --> N[Determine WebREPL Policy]
N --> O[Start WebREPL?]
O -- yes --> P[Start WebREPL]
O -- no --> Q[Complete]
P --> Q
Q -- asynchronous --> F
Q -- synchronous --> R[Return Success Status]
F --> B
```
Raw data
{
"_id": null,
"home_page": "https://github.com/mitchins/micropython-wifimanager",
"name": "micropython-wifimanager",
"maintainer": null,
"docs_url": null,
"requires_python": null,
"maintainer_email": null,
"keywords": "micropython, esp8266, esp32, wifi, manager",
"author": "Mitchell Currie",
"author_email": "mitch@mitchellcurrie.com",
"download_url": "https://files.pythonhosted.org/packages/e5/79/885e231b31b4f3c9c6dc076e50a09b89cf4fec3170a6d7670cfe0d996e42/micropython_wifimanager-1.0.2.tar.gz",
"platform": null,
"description": "# micropython-wifimanager\nA simple network configuration utility for MicroPython on boards such as ESP8266 and ESP32.\n\n#### Test Start\n\nUpload wifi_manager.py and your networks.json, then in the REPL:\n\n```python\n# simple_test.py \u2014 copy to board and run in REPL\nfrom wifi_manager import WifiManager\n\n# this should synchronously connect to your first known network\n# and return True/False immediately\nok = WifiManager.setup_network()\nprint(\"\u2705 network OK\" if ok else \"\u274c network failed\")\n```\n\n#### Production Usage\n\n##### a) Asynchronous, managed in background\nCreate main.py on your device:\n\n```python\nimport uasyncio as asyncio\nimport logging\nfrom wifi_manager import WifiManager\n\nlogging.basicConfig(level=logging.INFO)\nWifiManager.on_connection_change(lambda evt, **kw: print(\"Event:\", evt, kw))\n\n# start the periodic manager\nWifiManager.start_managing()\n\n# hand off to uasyncio\nasyncio.get_event_loop().run_forever()\n```\n\n> **Note:** scans and auto-reconnects every 10 s per your config.\n\n##### b) Auto-start on boot\n\n###### 1.\t`boot.py` (runs at power-on, no REPL)\n\n```python\n# boot.py\nimport machine, os\n# mount filesystem, etc.\n# then launch main.py automatically\ntry:\n import main\nexcept Exception as e:\n # fail-safe: at least bring up AP\n from wifi_manager import WifiManager\n WifiManager.setup_network()\n```\n###### 2.\t`main.py` (as above)\n\nWith that in place, on every reset your board will:\n\t\u2022\tRun boot.py\n\t\u2022\tHand off to your async manager in main.py,\n\t\u2022\tBring up either your known STA networks or fallback AP + WebREPL.\n\n#### Configuration\n\nSimply upload your JSON file with your networks, the default path is '/networks.json', which is specified in the class property `config_file`.\n\nA sample configuration may look like this:\n\n\t{\n\t\t\"schema\": 2,\n\t\t\"known_networks\": [\n\t\t\t{\n\t\t\t\t\"ssid\": \"User\\u2019s iPhone\",\n\t\t\t\t\"password\": \"Password1\",\n\t\t\t\t\"enables_webrepl\": false\n\t\t\t},\n\t\t\t{\n\t\t\t\t\"ssid\": \"HomeNetwork\",\n\t\t\t\t\"password\": \"Password2\",\n\t\t\t\t\"enables_webrepl\": true\n\t\t\t}\n\t\t],\n\t\t\"access_point\": {\n\t\t\t\"config\": {\n\t\t\t\t\"essid\": \"Micropython-Dev\",\n\t\t\t\t\"channel\": 11,\n\t\t\t\t\"hidden\": false,\n\t\t\t\t\"password\": \"P@55W0rd\"\n\t\t\t},\n\t\t\t\"enables_webrepl\": true,\n\t\t\t\"start_policy\": \"fallback\"\n\t\t},\n\t\t\"config_server\": {\n\t\t\t\"enabled\": false,\n\t\t\t\"password\": \"micropython\"\n\t\t}\n\t}\n\n#### Configuration schema\n\n* **schema**: currently this should be `2`\n* **known_networks**: list of networks to connect to, in order of most preferred first\n\t* SSID - the name of the access point\n\t* password - the clear-text password to use\n\t* enables_webrepl - a boolean value to indicate if connection to this network desires webrepl being started\n* **access_point**: the details for the access point (AP) of this device\n\t* config - the keys for the AP config, exactly as per the micropython documentation\n\t* enables_webrepl - a boolean value to indicate if ceating this network desires webrepl being started\n\t* start_policy - A policy from the below list to indicate when to enable the AP\n\t\t* 'always' - regardless of the connection to any base station, AP will be started\n\t\t* 'fallback' - the AP will only be started if no network could be connected to\n\t\t* 'never' - The AP will not be started under any condition\n* **config_server**: optional web configuration interface settings\n\t* enabled - boolean to enable/disable the web config interface\n\t* password - password for HTTP Basic Authentication (username is \"admin\")\n\n#### Simple usage (one shot)\n\nHere's an example of how to use the WifiManager.\n\n\tMicroPython v1.9.4 on 2018-05-11; ESP32 module with ESP32\n\tType \"help()\" for more information.\n\t>>> from wifi_manager import WifiManager\n\t>>> WifiManager.setup_network()\n\tconnecting to network Foo-Network...\n\tWebREPL daemon started on ws://10.1.1.234:8266\n\tStarted webrepl in normal mode\n\tTrue\n\n\n#### Asynchronous usage (event loop)\n\nThe WifiManager can be run asynchronously, via the cooperative scheduling that micropthon has in uasyncio. If you call `WifiManager.start_managing()` as follows, it will ensure that periodically the network status is scanned, and connection will be re-established as per preferences as needed.\n\n\timport uasyncio as asyncio\n\timport logging\n\tfrom wifi_manager import WifiManager\n\n\tlogging.basicConfig(level=logging.WARNING)\n\tWifiManager.start_managing()\n\tasyncio.get_event_loop().run_forever()\n\n#### Web configuration interface\n\nFor easier configuration management, WifiManager includes an optional web interface that allows you to view and edit the configuration remotely through a browser.\n\n**Enable in configuration:**\n```json\n{\n\t\"schema\": 2,\n\t\"known_networks\": [...],\n\t\"access_point\": {...},\n\t\"config_server\": {\n\t\t\"enabled\": true,\n\t\t\"password\": \"your-password-here\"\n\t}\n}\n```\n\n**Manual start:**\n```python\nfrom wifi_manager import WifiManager\nWifiManager.start_config_server(\"your-password\")\n```\n\n**Usage:**\n1. Connect to your device's network (either managed network or AP)\n2. Open browser to `http://[device-ip]:8080`\n3. Enter username \"admin\" and your configured password\n4. Edit JSON configuration in the web interface\n5. Click \"Save & Apply\" to update and restart networking\n\n**Features:**\n- Live JSON validation\n- Automatic network restart after changes\n- HTTP Basic Authentication protection\n- Works with any modern browser\n- Integrated with async event loop\n\n#### Connection state callbacks\n\nWifiManager can notify your application when the WiFi connection state changes, allowing you to respond to connectivity events in real-time.\n\n**Register a callback:**\n```python\ndef my_connection_handler(event, **kwargs):\n if event == 'connected':\n print(f\"Connected to {kwargs.get('ssid')} with IP {kwargs.get('ip')}\")\n # Turn on LED, start data collection, etc.\n elif event == 'disconnected':\n print(\"Lost WiFi connection\")\n # Turn off LED, pause operations, etc.\n elif event == 'ap_started':\n print(f\"Started access point: {kwargs.get('essid')}\")\n # Different LED color for AP mode\n elif event == 'connection_failed':\n print(f\"Failed to connect to: {kwargs.get('attempted_networks')}\")\n # Log failure, try alternative approach\n\nfrom wifi_manager import WifiManager\nWifiManager.on_connection_change(my_connection_handler)\nWifiManager.start_managing()\n```\n\n**Available events:**\n- `connected` - Successfully connected to a network (includes `ssid` and `ip`)\n- `disconnected` - Lost connection to network\n- `ap_started` - Access point was activated (includes `essid`)\n- `connection_failed` - All connection attempts failed (includes `attempted_networks`)\n\n**Features:**\n- Multiple callbacks supported\n- Automatic state change detection\n- Exception handling in callbacks won't crash the manager\n- Callbacks can be added/removed dynamically\n\n\n#### Contribution\n\nFound a bug, or want a feature? open an issue.\n\nIf you want to contribute, create a pull request.\n\n#### System flow\n\n```mermaid\ngraph TD\n A[Asynchronous Entry] -- start_managing --> B[Event Loop]\n C[Synchronous Entry] -- setup_network --> D[Load Config File]\n \n B -- manage --> E[Check Connection Status]\n E -- connected --> F[Sleep 10s]\n E -- disconnected --> D\n \n D -- success --> G[Activate WLAN]\n D -- file error --> D1[Use Default Config]\n D1 --> G\n \n G --> H[Scan Available Networks]\n H -- scan success --> I[Match & Rank Candidates]\n H -- scan error --> M[Configure AP]\n \n I --> J[Try Next Candidate]\n J -- has candidate --> K[Attempt Connection]\n J -- no candidates --> M\n \n K -- connected --> M\n K -- failed --> J\n \n M[Configure Access Point] --> N[Determine WebREPL Policy]\n N --> O[Start WebREPL?]\n O -- yes --> P[Start WebREPL]\n O -- no --> Q[Complete]\n P --> Q\n \n Q -- asynchronous --> F\n Q -- synchronous --> R[Return Success Status]\n \n F --> B\n```\n",
"bugtrack_url": null,
"license": null,
"summary": "A simple network configuration utility for MicroPython on the ESP-8266 and ESP-32 boards",
"version": "1.0.2",
"project_urls": {
"Download": "https://github.com/mitchins/micropython-wifimanager/archive/1.0.1.tar.gz",
"Homepage": "https://github.com/mitchins/micropython-wifimanager"
},
"split_keywords": [
"micropython",
" esp8266",
" esp32",
" wifi",
" manager"
],
"urls": [
{
"comment_text": null,
"digests": {
"blake2b_256": "122b8b34e32d7fc0b5a2abf81dac98e89ec6b2701dd66e4585f2bf467474ae85",
"md5": "a5ab6747a1b7dd15b5786d6da28b87da",
"sha256": "50a7c390d5fa0465db0e352db892748a9bcf446dd7498eec1e311782652da0a5"
},
"downloads": -1,
"filename": "micropython_wifimanager-1.0.2-py3-none-any.whl",
"has_sig": false,
"md5_digest": "a5ab6747a1b7dd15b5786d6da28b87da",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": null,
"size": 11044,
"upload_time": "2025-07-23T00:12:47",
"upload_time_iso_8601": "2025-07-23T00:12:47.529765Z",
"url": "https://files.pythonhosted.org/packages/12/2b/8b34e32d7fc0b5a2abf81dac98e89ec6b2701dd66e4585f2bf467474ae85/micropython_wifimanager-1.0.2-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": null,
"digests": {
"blake2b_256": "e579885e231b31b4f3c9c6dc076e50a09b89cf4fec3170a6d7670cfe0d996e42",
"md5": "dec858c709bdccd96e56dc383044bccb",
"sha256": "77db8a0ef6b53cf9435d1e3aa646ce27b60f2d8cf8397ef90f623bd0bf6a7b80"
},
"downloads": -1,
"filename": "micropython_wifimanager-1.0.2.tar.gz",
"has_sig": false,
"md5_digest": "dec858c709bdccd96e56dc383044bccb",
"packagetype": "sdist",
"python_version": "source",
"requires_python": null,
"size": 10871,
"upload_time": "2025-07-23T00:12:48",
"upload_time_iso_8601": "2025-07-23T00:12:48.460198Z",
"url": "https://files.pythonhosted.org/packages/e5/79/885e231b31b4f3c9c6dc076e50a09b89cf4fec3170a6d7670cfe0d996e42/micropython_wifimanager-1.0.2.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2025-07-23 00:12:48",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "mitchins",
"github_project": "micropython-wifimanager",
"travis_ci": false,
"coveralls": false,
"github_actions": false,
"lcname": "micropython-wifimanager"
}