Electric Imp WiFi experiments
After getting frustrated with a very sensitive process of doing the BlinkUp to my Electric Imp’s, I started to look into if it was possible to define more access points, and surely, there was a way! 🙂
I first started out with making something to just show what was around, and the result when accessing the agent url is something like this.
SSID: OpenWrt Channel: 1 dB: -58 Open: false SSID: Søblik Channel: 5 dB: -84 Open: false SSID: Mikey Channel: 9 dB: -59 Open: false
If you notice, OpenWrt is marked with bold, and Mikey with Italic. This is to indicate OpenWrt is the one the Impee is currently connected to, and Mikey got found while scanning, and we got info on how to connect to this. Søblik is just normal, because it was found, but we know nothing about how to log on to it.
Agent:
This is basically only what shows the test in the browser, all the data is coming from the device and is send over to the agent.
wifi <- ""; http.onrequest(function(request,res) { if (request.body == "") { local tempString = split(wifi, "|"); local output = "<pre>"; if (wifi.len() < 1) { output = "Waiting for the Impee to send some data to the Agent..."; } else { foreach(sub in tempString) { local subString = split(sub, ","); if (subString[0] == "1") { output += "SSID: <b>" + subString[1] + "</b>"; } else if (subString[0] == "2") { output += "SSID: <i>" + subString[1] + "</i>"; } else { output += "SSID: " + subString[1]; } if (subString[1].len() > 4 && subString[1].len() <= 9) { output += "\t"; } else if (subString[1].len() <= 4) { output += "\t\t"; } output += "\tChannel: " + subString[2]; output += "\tdB: " + subString[3]; output += "\t\tOpen: " + subString[4] + "\r\n"; } } output += "</pre>"; res.send(200, "<!DOCTYPE html><html><head><meta http-equiv=\"refresh\" content=\"2\"></head><body>" + output + "</body></html>"); } }); device.on("sendwifi", function(data) { wifi = data; }); device.onconnect(function() { server.log("device connected to agent"); }); device.ondisconnect(function() { server.log("device disconnected from agent"); });
Device:
Here is where the access points are scanned down, and where we also check if we know them or not.
In the bottom of the code there is something from the Electric Imp docs where they show how to change to another access point. This is a slightly modified version which fit into this application.
connections <- [ { ssid = "wifi1", pw = "key1" }, { ssid = "wifi2", pw = "key2" }, { ssid = "wifi3", pw = "key3" } ]; function scanwifi() { local scanResults = imp.scanwifinetworks(); local wifi = ""; foreach (idx,val in scanResults) { local connStatus = "0"; if (imp.getssid() == scanResults[idx].ssid) { connStatus = "1"; } else { foreach (idy,val in connections) { if (scanResults[idx].ssid == connections[idy].ssid) { connStatus = "2"; } } } wifi += connStatus + "," + scanResults[idx].ssid +"," + scanResults[idx].channel + "," + scanResults[idx].rssi + "," + scanResults[idx].open + "|"; } imp.wakeup(2, scanwifi); //Do this again in 1 minute agent.send("sendwifi", wifi); } scanwifi(); server.setsendtimeoutpolicy(RETURN_ON_ERROR, WAIT_TIL_SENT, 30); currentConnection connections.len()) { // go to sleep for 5 minutes currentConnection = 0; imp.deepsleepfor(5*60); } else { // if there are still connections to try // grab current ssid and pw, and increment currentConnection // for the next attempt (if connection fails) local ssid = connections[currentConnection].ssid; local pw = connections[currentConnection].pw; currentConnection++; // try connecting ChangeWifi(ssid, pw, ConnectOrFailToNextConnection) } } } // On boot, make sure we're connected // or try connecting ConnectOrFailToNextConnection(); // called after imp tries to reconnect to current // server for 1 minute and fails server.onunexpecteddisconnect(function(reason) { // Loop through connections until we connect currentConnection = 0; ConnectOrFailToNextConnection(); });