Browse Source

Moved configuration to Embedis

fastled
Xose Pérez 7 years ago
parent
commit
4f269713c4
12 changed files with 185 additions and 272 deletions
  1. +0
    -112
      code/src/Config.cpp
  2. +0
    -69
      code/src/Config.h
  3. +12
    -0
      code/src/defaults.h
  4. +17
    -7
      code/src/emon.ino
  5. +10
    -14
      code/src/main.ino
  6. +20
    -11
      code/src/mqtt.ino
  7. +3
    -2
      code/src/nofuss.ino
  8. +1
    -1
      code/src/ota.ino
  9. +2
    -2
      code/src/rf.ino
  10. +58
    -0
      code/src/settings.ino
  11. +51
    -49
      code/src/webserver.ino
  12. +11
    -5
      code/src/wifi.ino

+ 0
- 112
code/src/Config.cpp View File

@ -1,112 +0,0 @@
/*
Config
Configuration file
*/
#include "Config.h"
#include "EEPROM.h"
bool ConfigClass::save() {
#ifdef DEBUG
Serial.println("[CONFIG] Saving");
#endif
String content;
content += "hostname=" + hostname + "|";
content += "ssid0=" + ssid[0] + "|";
content += "pass0=" + pass[0] + "|";
content += "ssid1=" + ssid[1] + "|";
content += "pass1=" + pass[1] + "|";
content += "ssid2=" + ssid[2] + "|";
content += "pass2=" + pass[2] + "|";
content += "mqttServer=" + mqttServer + "|";
content += "mqttPort=" + mqttPort + "|";
content += "mqttTopic=" + mqttTopic + "|";
content += "rfChannel=" + rfChannel + "|";
content += "rfDevice=" + rfDevice + "|";
content += "nofussServer=" + nofussServer + "|";
content += "nofussInterval=" + nofussInterval + "|";
content += "pwMainsVoltage=" + pwMainsVoltage + "|";
content += "pwCurrentRatio=" + pwCurrentRatio + "|";
Serial.print("[CONFIG] ");
Serial.println(content);
EEPROM.write(CONFIG_START, CONFIG_VERSION);
for (int i=0; i<content.length(); i++) {
EEPROM.write(CONFIG_START + i + 1, content.charAt(i));
}
EEPROM.write(CONFIG_START + content.length() + 1, 0);
EEPROM.commit();
return true;
}
bool ConfigClass::load() {
#ifdef DEBUG
Serial.println("[CONFIG] Loading");
#endif
int version = EEPROM.read(CONFIG_START);
if (version != CONFIG_VERSION) {
#ifdef DEBUG
Serial.println("[CONFIG] Wrong version");
#endif
return false;
}
String content;
char character;
int position = 0;
do {
character = EEPROM.read(CONFIG_START + 1 + position);
content += character;
position++;
} while (character > 0);
Serial.print("[CONFIG] ");
Serial.println(content);
int start = 0;
int end = content.indexOf("|", start);
while (end > 0) {
String line = content.substring(start, end);
if (line.startsWith("hostname=")) hostname = line.substring(9);
else if (line.startsWith("ssid0=")) ssid[0] = line.substring(6);
else if (line.startsWith("pass0=")) pass[0] = line.substring(6);
else if (line.startsWith("ssid1=")) ssid[1] = line.substring(6);
else if (line.startsWith("pass1=")) pass[1] = line.substring(6);
else if (line.startsWith("ssid2=")) ssid[2] = line.substring(6);
else if (line.startsWith("pass2=")) pass[2] = line.substring(6);
else if (line.startsWith("mqttServer=")) mqttServer = line.substring(11);
else if (line.startsWith("mqttPort=")) mqttPort = line.substring(9);
else if (line.startsWith("mqttTopic=")) mqttTopic = line.substring(10);
else if (line.startsWith("rfChannel=")) rfChannel = line.substring(10);
else if (line.startsWith("rfDevice=")) rfDevice = line.substring(9);
else if (line.startsWith("nofussServer=")) nofussServer = line.substring(13);
else if (line.startsWith("nofussInterval=")) nofussInterval = line.substring(15);
else if (line.startsWith("pwMainsVoltage=")) pwMainsVoltage = line.substring(15);
else if (line.startsWith("pwCurrentRatio=")) pwCurrentRatio = line.substring(15);
if (end < 0) break;
start = end + 1;
end = content.indexOf("|", start);
}
#ifdef DEBUG
Serial.println("[CONFIG] OK");
#endif
return true;
}
ConfigClass config;

+ 0
- 69
code/src/Config.h View File

@ -1,69 +0,0 @@
/*
Config
Configuration file
*/
#ifndef Config_h
#define Config_h
#include "Arduino.h"
// -----------------------------------------------------------------------------
// Defaults
// -----------------------------------------------------------------------------
#define CONFIG_START 128
#define CONFIG_VERSION 0x81
#define NETWORK_BUFFER 3
#define MQTT_SERVER "192.168.1.100"
#define MQTT_PORT 1883
#define MQTT_TOPIC "/test/switch/{identifier}"
#define NOFUSS_SERVER "http://192.168.1.100"
#define NOFUSS_INTERVAL 600000
#define MAINS_VOLTAGE 230
#define CURRENT_RATIO 180
#define RF_CHANNEL 31
#define RF_DEVICE 1
// -----------------------------------------------------------------------------
// Class definition
// -----------------------------------------------------------------------------
class ConfigClass {
public:
String hostname;
String ssid[NETWORK_BUFFER];
String pass[NETWORK_BUFFER];
String mqttServer = MQTT_SERVER;
String mqttPort = String(MQTT_PORT);
String mqttTopic = MQTT_TOPIC;
String mqttUser = "";
String mqttPassword = "";
String rfChannel = String(RF_CHANNEL);
String rfDevice = String(RF_DEVICE);
String nofussServer = String(NOFUSS_SERVER);
String nofussInterval = String(NOFUSS_INTERVAL);
String pwMainsVoltage = String(MAINS_VOLTAGE);
String pwCurrentRatio = String(CURRENT_RATIO);
bool save();
bool load();
};
extern ConfigClass config;
#endif

+ 12
- 0
code/src/defaults.h View File

@ -54,6 +54,7 @@
#define HEARTBEAT_INTERVAL 60000
#define FS_VERSION_FILE "/fsversion"
#define WIFI_MAX_NETWORKS 3
#define WIFI_RECONNECT_INTERVAL 300000
#define RF_PIN 14
@ -63,6 +64,9 @@
#define DHT_TYPE DHT22
#define DHT_TIMING 11
#define MQTT_SERVER "192.168.1.100"
#define MQTT_PORT 1883
#define MQTT_TOPIC "/test/switch/{identifier}"
#define MQTT_RECONNECT_DELAY 10000
#define MQTT_RETAIN true
#define MQTT_STATUS_TOPIC ""
@ -74,6 +78,12 @@
#define MQTT_TEMPERATURE_TOPIC "/temperature"
#define MQTT_HUMIDITY_TOPIC "/humidity"
#define NOFUSS_SERVER "http://192.168.1.100"
#define NOFUSS_INTERVAL 600000
#define RF_CHANNEL 31
#define RF_DEVICE 1
#define EMON_CURRENT_PIN 0
#define EMON_SAMPLES 1000
#define EMON_INTERVAL 10000
@ -82,3 +92,5 @@
#define EMON_REFERENCE_VOLTAGE 1.0
#define EMON_CURRENT_PRECISION 1
#define EMON_CURRENT_OFFSET 0.25
#define EMON_MAINS_VOLTAGE 230
#define EMON_CURRENT_RATIO 180

+ 17
- 7
code/src/emon.ino View File

@ -11,24 +11,32 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
#include <EmonLiteESP.h>
EmonLiteESP power;
EmonLiteESP emon;
double current;
// -----------------------------------------------------------------------------
// EMON
// -----------------------------------------------------------------------------
void setCurrentRatio(float value) {
emon.setCurrentRatio(value);
}
double getCurrent() {
return current;
}
unsigned int currentCallback() {
return analogRead(EMON_CURRENT_PIN);
}
void powerMonitorSetup() {
power.initCurrent(currentCallback, EMON_ADC_BITS, EMON_REFERENCE_VOLTAGE, config.pwCurrentRatio.toFloat());
power.setPrecision(EMON_CURRENT_PRECISION);
emon.initCurrent(
currentCallback,
EMON_ADC_BITS,
EMON_REFERENCE_VOLTAGE,
getSetting("pwCurrentRatio", String(EMON_CURRENT_RATIO)).toFloat()
);
emon.setPrecision(EMON_CURRENT_PRECISION);
}
void powerMonitorLoop() {
@ -47,7 +55,7 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
if (!digitalRead(RELAY_PIN)) {
current = 0;
} else {
current = power.getCurrent(EMON_SAMPLES);
current = emon.getCurrent(EMON_SAMPLES);
current -= EMON_CURRENT_OFFSET;
if (current < 0) current = 0;
}
@ -61,15 +69,17 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
sum += current;
++measurements;
float mainsVoltage = getSetting("pwMainsVoltage", String(EMON_MAINS_VOLTAGE)).toFloat();
#ifdef DEBUG
Serial.print(F("[ENERGY] Power now: "));
Serial.print(int(current * config.pwMainsVoltage.toFloat()));
Serial.print(int(current * mainsVoltage));
Serial.println(F("W"));
#endif
if (measurements == EMON_MEASUREMENTS) {
char buffer[8];
double power = (sum - max - min) * config.pwMainsVoltage.toFloat() / (measurements - 2);
double power = (sum - max - min) * mainsVoltage / (measurements - 2);
sprintf(buffer, "%d", int(power));
mqttSend((char *) MQTT_POWER_TOPIC, buffer);
sum = 0;


+ 10
- 14
code/src/main.ino View File

@ -18,15 +18,12 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
extern "C" {
#include "user_interface.h"
}
#include <Arduino.h>
#include "version.h"
#include "defaults.h"
#include "FS.h"
#include "Config.h"
String getSetting(const String& key, String defaultValue = "");
// -----------------------------------------------------------------------------
// Methods
@ -169,19 +166,16 @@ void welcome() {
void setup() {
hardwareSetup();
settingsSetup();
setSetting("hostname", String() + getIdentifier());
saveSettings();
relaySetup();
buttonSetup();
delay(1000);
delay(2000);
welcome();
config.load();
// At the moment I am overriding any possible hostname stored in EEPROM
// with the generated one until I have a way to change them from the
// configuration interface
config.hostname = getIdentifier();
wifi_station_set_hostname((char *) config.hostname.c_str());
buttonSetup();
wifiSetup();
otaSetup();
mqttSetup();
webServerSetup();
@ -223,6 +217,8 @@ void loop() {
powerMonitorLoop();
#endif
settingsLoop();
delay(1);
}

+ 20
- 11
code/src/mqtt.ino View File

@ -23,10 +23,14 @@ bool mqttConnected() {
return mqtt.connected();
}
void mqttDisconnect() {
mqtt.disconnect();
}
void buildTopics() {
// Replace identifier
mqttTopic = config.mqttTopic;
mqttTopic.replace("{identifier}", config.hostname);
mqttTopic = getSetting("mqttTopic", MQTT_TOPIC);
mqttTopic.replace("{identifier}", getSetting("hostname"));
}
void mqttSend(char * topic, char * message) {
@ -78,31 +82,36 @@ void mqttCallback(char* topic, byte* payload, unsigned int length) {
void mqttConnect() {
if (!mqtt.connected() && (config.mqttServer.length()>0)) {
String mqttServer = getSetting("mqttServer", MQTT_SERVER);
int mqttPort = getSetting("mqttPort", String(MQTT_PORT)).toInt();
String mqttUser = getSetting("mqttUser");
String mqttPassword = getSetting("mqttPassword");
if (!mqtt.connected() && (mqttServer.length()>0)) {
mqtt.setServer((const char *) config.mqttServer.c_str(), config.mqttPort.toInt());
mqtt.setServer((const char *) mqttServer.c_str(), mqttPort);
#ifdef DEBUG
Serial.print(F("[MQTT] Connecting to broker at "));
Serial.print(config.mqttServer);
Serial.print(mqttServer);
#endif
if (config.mqttUser.length() > 0) {
if (mqttUser.length() > 0) {
#ifdef DEBUG
Serial.print(F(" as user "));
Serial.print(config.mqttUser);
Serial.print(mqttUser);
Serial.print(F(": "));
#endif
mqtt.connect(
config.hostname.c_str(),
(const char *) config.mqttUser.c_str(),
(const char *) config.mqttPassword.c_str()
getSetting("hostname").c_str(),
(const char *) mqttUser.c_str(),
(const char *) mqttPassword.c_str()
);
} else {
#ifdef DEBUG
Serial.print(F(" anonymously: "));
#endif
mqtt.connect(config.hostname.c_str());
mqtt.connect(getSetting("hostname").c_str());
}
if (mqtt.connected()) {


+ 3
- 2
code/src/nofuss.ino View File

@ -17,7 +17,7 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
void nofussSetup() {
NoFUSSClient.setServer(config.nofussServer);
NoFUSSClient.setServer(getSetting("nofussServer", NOFUSS_SERVER));
NoFUSSClient.setDevice(DEVICE);
NoFUSSClient.setVersion(APP_VERSION);
@ -79,7 +79,8 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
static unsigned long last_check = 0;
if (!wifiConnected()) return;
if ((last_check > 0) && ((millis() - last_check) < config.nofussInterval.toInt())) return;
unsigned long interval = getSetting("nofussInterval", String(NOFUSS_INTERVAL)).toInt();
if ((last_check > 0) && ((millis() - last_check) < interval)) return;
last_check = millis();
NoFUSSClient.handle();


+ 1
- 1
code/src/ota.ino View File

@ -17,7 +17,7 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
void otaSetup() {
ArduinoOTA.setPort(OTA_PORT);
ArduinoOTA.setHostname(config.hostname.c_str());
ArduinoOTA.setHostname(getSetting("hostname").c_str());
ArduinoOTA.setPassword((const char *) OTA_PASS);
ArduinoOTA.onStart([]() {


+ 2
- 2
code/src/rf.ino View File

@ -43,7 +43,7 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
unsigned long code = 0;
// channel
unsigned int channel = config.rfChannel.toInt();
unsigned int channel = getSetting("rfChannel", String(RF_CHANNEL)).toInt();
for (byte i = 0; i < 5; i++) {
code *= 3;
if (channel & 1) code += 1;
@ -51,7 +51,7 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
}
// device
unsigned int device = config.rfDevice.toInt();
unsigned int device = getSetting("rfDevice", String(RF_DEVICE)).toInt();
for (byte i = 0; i < 5; i++) {
code *= 3;
if (device != i) code += 2;


+ 58
- 0
code/src/settings.ino View File

@ -0,0 +1,58 @@
/*
ESPurna
SETTINGS MODULE
Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
*/
#include "Embedis.h"
#include <EEPROM.h>
#include "spi_flash.h"
#define AUTO_SAVE 0
Embedis embedis(Serial);
// -----------------------------------------------------------------------------
// Settings
// -----------------------------------------------------------------------------
void settingsSetup() {
EEPROM.begin(SPI_FLASH_SEC_SIZE);
Embedis::dictionary( F("EEPROM"),
SPI_FLASH_SEC_SIZE,
[](size_t pos) -> char { return EEPROM.read(pos); },
[](size_t pos, char value) { EEPROM.write(pos, value); },
#if AUTO_SAVE
[]() { EEPROM.commit(); }
#else
[]() {}
#endif
);
}
void settingsLoop() {
embedis.process();
}
String getSetting(const String& key, String defaultValue) {
String value;
if (!Embedis::get(key, value)) value = defaultValue;
return value;
}
bool setSetting(const String& key, String& value) {
return Embedis::set(key, value);
}
bool delSetting(const String& key) {
return Embedis::del(key);
}
void saveSettings() {
#if not AUTO_SAVE
EEPROM.commit();
#endif
}

+ 51
- 49
code/src/webserver.ino View File

@ -91,32 +91,30 @@ void handleInit() {
root["appname"] = String(buffer);
root["manufacturer"] = String(MANUFACTURER);
root["device"] = String(DEVICE);
root["hostname"] = config.hostname;
root["network"] = (WiFi.status() == WL_CONNECTED) ? WiFi.SSID() : "ACCESS POINT";
root["ip"] = (WiFi.status() == WL_CONNECTED) ? WiFi.localIP().toString() : WiFi.softAPIP().toString();
root["hostname"] = getSetting("hostname");
root["network"] = getNetwork();
root["ip"] = getIP();
root["updateInterval"] = STATUS_UPDATE_INTERVAL;
root["ssid0"] = config.ssid[0];
root["pass0"] = config.pass[0];
root["ssid1"] = config.ssid[1];
root["pass1"] = config.pass[1];
root["ssid2"] = config.ssid[2];
root["pass2"] = config.pass[2];
for (byte i=0; i<WIFI_MAX_NETWORKS; i++) {
root["ssid" + String(i)] = getSetting("ssid" + String(i));
root["pass" + String(i)] = getSetting("pass" + String(i));
}
root["mqttServer"] = config.mqttServer;
root["mqttPort"] = config.mqttPort;
root["mqttUser"] = config.mqttUser;
root["mqttPassword"] = config.mqttPassword;
root["mqttTopic"] = config.mqttTopic;
root["mqttServer"] = getSetting("mqttServer", MQTT_SERVER);
root["mqttPort"] = getSetting("mqttPort", String(MQTT_PORT));
root["mqttUser"] = getSetting("mqttUser");
root["mqttPassword"] = getSetting("mqttPassword");
root["mqttTopic"] = getSetting("mqttTopic", MQTT_TOPIC);
#if ENABLE_RF
root["rfChannel"] = config.rfChannel;
root["rfDevice"] = config.rfDevice;
root["rfChannel"] = getSetting("rfChannel", String(RF_CHANNEL));
root["rfDevice"] = getSetting("rfDevice", String(RF_DEVICE));
#endif
#if ENABLE_EMON
root["pwMainsVoltage"] = config.pwMainsVoltage;
root["pwCurrentRatio"] = config.pwCurrentRatio;
root["pwMainsVoltage"] = getSetting("pwMainsVoltage", String(EMON_MAINS_VOLTAGE));
root["pwCurrentRatio"] = getSetting("pwCurrentRatio", String(EMON_CURRENT_RATIO));
#endif
String output;
@ -137,9 +135,9 @@ void handleStatus() {
StaticJsonBuffer<256> jsonBuffer;
JsonObject& root = jsonBuffer.createObject();
root["relay"] = digitalRead(RELAY_PIN) ? 1: 0;
root["mqtt"] = mqtt.connected() ? 1: 0;
root["mqtt"] = mqttConnected();
#if ENABLE_EMON
root["power"] = getCurrent() * config.pwMainsVoltage.toFloat();
root["power"] = getCurrent() * getSetting("pwMainsVoltage", String(EMON_MAINS_VOLTAGE)).toFloat();
#endif
#if ENABLE_DHT
root["temperature"] = getTemperature();
@ -158,48 +156,52 @@ void handleSave() {
Serial.println(F("[WEBSERVER] Request: /save"));
#endif
if (server.hasArg("status")) {
if (server.arg("status") == "1") {
switchRelayOn();
} else {
switchRelayOff();
bool disconnectMQTT = false;
for (unsigned int i=0; i<server.args(); i++) {
String key = server.argName(i);
String value = server.arg(i);
if (key == "status") {
if (value == "1") {
switchRelayOn();
} else {
switchRelayOff();
}
continue;
}
}
if (server.hasArg("ssid0")) config.ssid[0] = server.arg("ssid0");
if (server.hasArg("pass0")) config.pass[0] = server.arg("pass0");
if (server.hasArg("ssid1")) config.ssid[1] = server.arg("ssid1");
if (server.hasArg("pass1")) config.pass[1] = server.arg("pass1");
if (server.hasArg("ssid2")) config.ssid[2] = server.arg("ssid2");
if (server.hasArg("pass2")) config.pass[2] = server.arg("pass2");
// Check wether we will have to reconfigure MQTT connection
if (!disconnectMQTT && key.startsWith("mqtt")) {
if (value != getSetting(key)) disconnectMQTT = true;
}
if (server.hasArg("mqttServer")) config.mqttServer = server.arg("mqttServer");
if (server.hasArg("mqttPort")) config.mqttPort = server.arg("mqttPort");
if (server.hasArg("mqttUser")) config.mqttUser = server.arg("mqttUser");
if (server.hasArg("mqttPassword")) config.mqttPassword = server.arg("mqttPassword");
if (server.hasArg("mqttTopic")) config.mqttTopic = server.arg("mqttTopic");
if (value != getSetting(key)) setSetting(key, value);
#if ENABLE_RF
if (server.hasArg("rfChannel")) config.rfChannel = server.arg("rfChannel");
if (server.hasArg("rfDevice")) config.rfDevice = server.arg("rfDevice");
#endif
#if ENABLE_EMON
if (server.hasArg("pwMainsVoltage")) config.pwMainsVoltage = server.arg("pwMainsVoltage");
if (server.hasArg("pwCurrentRatio")) config.pwCurrentRatio = server.arg("pwCurrentRatio");
#endif
}
server.send(202, "text/json", "{}");
config.save();
saveSettings();
#if ENABLE_RF
rfBuildCodes();
#endif
#if ENABLE_EMON
power.setCurrentRatio(config.pwCurrentRatio.toFloat());
setCurrentRatio(getSetting("pwCurrentRatio").toFloat());
#endif
// Disconnect from current WIFI network, wifiLoop will take care of the reconnection
wifiDisconnect();
// Disconnect from current WIFI network if it's not the first on the list
// wifiLoop will take care of the reconnection
if (getNetwork() != getSetting("ssid0")) {
wifiDisconnect();
// else check if we should reconigure MQTT connection
} else if (disconnectMQTT) {
mqttDisconnect();
}
}


+ 11
- 5
code/src/wifi.ino View File

@ -9,6 +9,10 @@ Copyright (C) 2016 by Xose Pérez <xose dot perez at gmail dot com>
#include "JustWifi.h"
extern "C" {
#include "user_interface.h"
}
JustWifi jw;
unsigned long wifiLastConnectionTime = 0;
@ -38,12 +42,14 @@ bool wifiConnected() {
void wifiSetup() {
wifi_station_set_hostname((char *) getSetting("hostname").c_str());
// Message callbacks
jw.onMessage([](justwifi_messages_t code, char * parameter) {
// Disconnect from MQTT server if no WIFI
if (code != MESSAGE_CONNECTED) {
if (mqtt.connected()) mqtt.disconnect();
if (mqttConnected()) mqttDisconnect();
}
#if DEBUG
@ -109,7 +115,7 @@ void wifiSetup() {
bool wifiAP() {
//jw.disconnect();
return jw.startAP((char *) config.hostname.c_str(), (char *) AP_PASS);
return jw.startAP((char *) getSetting("hostname").c_str(), (char *) AP_PASS);
}
void wifiConnect() {
@ -120,9 +126,9 @@ void wifiConnect() {
// Set networks
jw.cleanNetworks();
jw.addNetwork((char *) config.ssid[0].c_str(), (char *) config.pass[0].c_str());
jw.addNetwork((char *) config.ssid[1].c_str(), (char *) config.pass[1].c_str());
jw.addNetwork((char *) config.ssid[2].c_str(), (char *) config.pass[2].c_str());
jw.addNetwork((char *) getSetting("ssid0").c_str(), (char *) getSetting("pass0").c_str());
jw.addNetwork((char *) getSetting("ssid1").c_str(), (char *) getSetting("pass1").c_str());
jw.addNetwork((char *) getSetting("ssid2").c_str(), (char *) getSetting("pass2").c_str());
// Connecting
if (!jw.autoConnect()) {


Loading…
Cancel
Save