114 Commits
alfa ... dev

Author SHA1 Message Date
JonatanRek
12212d6c56 Release Fixes 2020-03-25 15:58:47 +01:00
JonatanRek
b2a8734ed3 API at home fix 2020-03-17 09:17:01 +01:00
3feeaab086 Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2020-03-16 17:09:07 +01:00
8cacccbf88 fix nodemcu 2020-03-16 17:08:47 +01:00
JonatanRek
8ab0b043f9 Api Impruvement 2020-03-16 16:34:37 +01:00
JonatanRek
24072cb582 Some tweeks 2020-03-16 15:07:44 +01:00
JonatanRek
801e26dda9 Updater Log Message + api tweeks 2020-03-16 15:03:43 +01:00
JonatanRek
ceeb002b6e Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2020-03-16 14:52:45 +01:00
JonatanRek
f570556d85 Bether Log + Log Wia API 2020-03-16 14:52:36 +01:00
b5d48be64a edit script to react on command 2020-03-13 17:02:53 +01:00
JonatanRek
e14a0edb3c Nicer Json 2020-03-13 16:28:50 +01:00
JonatanRek
ca2cb2dbd2 API fix 2020-03-13 16:25:09 +01:00
JonatanRek
62449d2528 Command interface API 2020-03-13 16:20:14 +01:00
JonatanRek
0d0ba4ae50 API command interface 2020-03-13 16:14:22 +01:00
JonatanRek
942c7a4bca New Stiles 2020-03-13 14:53:05 +01:00
JonatanRek
aaa713e646 Better Notification on Device Update. 2020-03-13 14:45:12 +01:00
Kotrba Filip
9d52a86aa8 little edit on shelly 2020-03-12 22:31:59 +01:00
unknown
a2030d944f setting for nodemcu 2020-03-12 22:14:36 +01:00
unknown
0b92c0a84a fix updater and other things 2020-03-12 21:34:12 +01:00
JonatanRek
3ff5e0d660 Chart Color 2020-03-12 10:28:36 +01:00
b158f4a042 fix upoad file 2020-03-11 15:30:11 +01:00
b05fa3e1ed add upload updater file 2020-03-11 14:45:42 +01:00
50100fd4c5 Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2020-03-11 13:11:14 +01:00
7825cbb7aa edit sonoff script on shelly script 2020-03-11 13:10:42 +01:00
JonatanRek
94f78af31b Diagnostic Information update 2020-03-11 12:43:37 +01:00
JonatanRek
6184f3815f Updater Ip address Filtration 2020-03-11 12:23:49 +01:00
JonatanRek
44c4c84292 Firmware Updater (Backend + GUI) 2020-03-11 12:22:44 +01:00
unknown
0d076eb67c some modification on shelly 2020-03-10 18:59:06 +01:00
unknown
3a6706d1ac fix nodemcu esp8266 2020-03-10 18:57:35 +01:00
9a8ea80f37 esp nodemcu version 4 2020-03-10 16:42:38 +01:00
unknown
e8def0f4ae Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2020-03-09 19:47:16 +01:00
unknown
f4ee4d5a7c fix updater 2020-03-09 19:45:49 +01:00
437d6f32c0 Smazat „app/updater/3C71BF2BEA66.bin“ 2020-03-09 19:45:21 +01:00
Kotrba Filip
b16766c65e fix shelly 1 2020-03-04 22:44:01 +01:00
unknown
b1b8c4925b fix merge 2020-03-04 20:56:31 +01:00
unknown
e2f7d72cb3 merge 2020-03-04 19:53:18 +01:00
unknown
a8daa51413 some test edit 2020-03-04 19:51:17 +01:00
JonatanRek
9d9bdc192f Create .gitkeep
Git keep
2020-03-04 15:45:31 +01:00
JonatanRek
eb62f02510 ESP Updater 2020-03-04 15:44:55 +01:00
JonatanRek
5d25eeccaf Update Shelly1_v2.ino
Double switch fix
2020-03-04 15:27:49 +01:00
Kotrba Filip
f3ec7476b2 little edit shelly 2020-03-03 20:03:06 +01:00
unknown
029d75cd33 Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2020-03-02 20:35:36 +01:00
unknown
4b1a26cc6f create shelly V2 2020-03-02 20:35:20 +01:00
JonatanRek
74e427fee2 Dore connection error ignor 2020-02-25 15:02:16 +01:00
JonatanRek
1e973d2d8f Automation Execution Time & Owner 2020-02-21 14:25:25 +01:00
JonatanRek
d8c7a54446 Automations 2020-02-21 14:01:39 +01:00
Kotrba Filip
edf0b1ceb4 wifi setting 2020-02-21 00:50:51 +01:00
unknown
ccd064ad3c add new shelly in alfa creation 2020-02-20 20:36:58 +01:00
unknown
dc4433899a fix 2020-02-20 19:04:43 +01:00
unknown
8a0f4d1956 some edit 2020-02-20 18:53:41 +01:00
unknown
c43b751bd3 merge 2020-02-18 21:31:37 +01:00
unknown
5a06a6c85a some fix and new firmware for shelly1 2020-02-18 21:30:44 +01:00
JonatanRek
15d95dae1d Fallback better settings 2020-02-15 14:02:18 +01:00
JonatanRek
bcd5f52a65 Fallback Fix 2020-02-14 17:05:56 +01:00
JonatanRek
0b8ad755a0 BACKGROUND SINC 2020-02-13 17:39:58 +01:00
JonatanRek
f0e82de775 Log page Fixes 2020-02-13 13:57:22 +01:00
JonatanRek
4ab9ad9c7c Log Clean Up "LogKeeper" initial 2020-02-13 13:53:58 +01:00
JonatanRek
1b5630215b API Request 2020-02-13 13:35:15 +01:00
JonatanRek
bc54e33621 Log Rest api requests 2020-02-13 13:32:18 +01:00
JonatanRek
e76b3127f3 FallBack Start 2020-02-11 16:01:00 +01:00
JonatanRek
a0fdd324e2 Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2020-02-11 15:09:51 +01:00
JonatanRek
cb95a0f9b8 LNG 2020-02-11 15:09:15 +01:00
unknown
fc7689b5a6 add edit on owen server 2020-02-06 17:57:11 +01:00
xinatorus
21bcff9660 gitignore 2020-01-27 21:08:32 +01:00
JonatanRek
c499a83a0c User Gavatar Support 2020-01-21 11:24:50 +01:00
JonatanRek
84f130faf3 //TODO 2020-01-17 10:28:09 +01:00
JonatanRek
3479fb9c87 DEBUGMODE in FRONTEND 2020-01-17 10:27:51 +01:00
JonatanRek
f345419c39 //TODO 2020-01-17 08:13:34 +01:00
JonatanRek
2dd2b3c6f7 User Manager Class Tweaks 2020-01-17 08:12:50 +01:00
JonatanRek
db3ab9dd95 Person at home detection 2020-01-17 08:12:40 +01:00
JonatanRek
dd8743d33e Ftp ignor 2020-01-16 14:51:30 +01:00
JonatanRek
842cbde2d8 Todo File addet 2020-01-16 14:50:39 +01:00
JonatanRek
ad89a18093 Periodical sync from dev FTP 2020-01-16 14:33:11 +01:00
unknown
6f0fa2f81e Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2020-01-11 11:23:01 +01:00
unknown
8e9639c257 edit sonoff basic 2020-01-11 11:22:23 +01:00
ŠPANINGER Václav
1e5564a11a Door/Window Senzor
Gerber Files + Schemes
2020-01-02 12:09:34 +01:00
JonatanRek
e1a7b69fee Battery measurement Added 2020-01-01 00:56:37 +01:00
JonatanRek
65e218e47b Door Windows Senzor Code + Case Addet 2019-12-31 23:08:43 +01:00
JonatanRek
cda98cdf77 Door Senzor 3D printable Case 2019-12-31 23:05:44 +01:00
JonatanRek
48fcd1a7c9 Notifications Icons Added 2019-12-31 23:05:19 +01:00
unknown
2d7db196dd fix digital pin and not commited changes in esp os node v3 2019-12-19 23:15:44 +01:00
unknown
ded59cc24a fix led 2019-12-12 19:44:17 +01:00
unknown
b1dd8dc297 sonoff version 3 created 2019-12-09 21:00:19 +01:00
JonatanRek
eddccead63 Update index.html
Some Tweeks
2019-12-01 15:56:40 +01:00
JonatanRek
ff3c796484 WIFI COnfiguration Page #2 2019-12-01 14:22:08 +01:00
JonatanRek
8b6a12c811 Minimalistic WiFI configuration page 2019-12-01 14:20:06 +01:00
JonatanRek
55cc65eddb Blinking on Wifi Connecting 2019-12-01 14:19:34 +01:00
JonatanRek
3bca87a4b3 Minore FW Tweeks 2019-11-30 18:35:45 +01:00
JonatanRek
563999e92d Network Setting 2019-11-28 14:34:32 +01:00
JonatanRek
b2e4da37bf STRING TO CHAR 2019-11-28 13:13:43 +01:00
JonatanRek
65439922b1 More functions 2019-11-28 08:45:51 +01:00
JonatanRek
4229c44678 Merge FW 2019-11-28 08:34:50 +01:00
JonatanRek
3fc6e931ef Merge 2019-11-28 08:33:43 +01:00
JonatanRek
e0ee40cb0d Device network setting part 1 2019-11-27 19:48:59 +01:00
JonatanRek
0045d00abc Comments, Comments Everywhere 2019-11-27 19:48:41 +01:00
JonatanRek
2b1ae58d55 Some tweeks 2019-11-27 19:15:13 +01:00
JonatanRek
5418452da2 Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2019-11-27 19:13:15 +01:00
JonatanRek
d67bac14e9 Fixes 2019-11-27 19:12:25 +01:00
JonatanRek
3b72bf85fd Merge Local Fixes NTB2 2019-11-27 19:11:43 +01:00
JonatanRek
b620ea6c8f Merge branch 'dev' of https://git.steelants.cz/JonatanRek/PHP_SMART_HOME_V3 into dev 2019-11-27 19:11:19 +01:00
JonatanRek
aef242ceca Clean Up 2019-11-27 19:10:29 +01:00
JonatanRek
8975eb785b FW tweeks 2019-11-27 18:18:46 +01:00
JonatanRek
878186c2a2 FW Clean Up 2019-11-27 17:29:20 +01:00
JonatanRek
1e7f16d3b9 Firmware impruevement #2 2019-11-27 17:27:18 +01:00
JonatanRek
79864c23fd Firmware impruevement 2019-11-27 17:19:22 +01:00
JonatanRek
7337e3c7d9 Static ip generator :) 2019-11-27 17:05:49 +01:00
JonatanRek
9e6968bf6c FW v3 TWEEKS 2019-11-26 13:56:06 +01:00
JonatanRek
3e71be821c Little Tweeks on Light Value Handling 2019-11-26 13:32:45 +01:00
JonatanRek
a5a5baffc9 API Sleep Time Fix 2019-11-26 13:32:08 +01:00
JonatanRek
88152ebeae Room Management In Settings 2019-11-22 15:09:22 +01:00
JonatanRek
2fdc1b5bcc ADDITIONAL SETTING (STATIC IP + TYPE)
Minor Fixes of Device EDit
2019-11-22 15:08:24 +01:00
JonatanRek
b26ab5c032 Formát #2 2019-11-22 15:07:54 +01:00
JonatanRek
6dbd4885e2 Format 2019-11-22 15:04:28 +01:00
JonatanRek
7d2bc0c6d6 New Updated Node Code 2019-11-04 15:51:30 +01:00
77 changed files with 35370 additions and 265 deletions

View File

@@ -2,4 +2,5 @@
_FIRMWARE _FIRMWARE
_INSTALATION _INSTALATION
_README_IMG _README_IMG
README.md README.md
.todo

4
.gitignore vendored
View File

@@ -1,7 +1,11 @@
.ftpconfig .ftpconfig
.ftpconfig2
config.php config.php
_nemazat/index.html _nemazat/index.html
_nemazat/css/main.css.map _nemazat/css/main.css.map
_nemazat/css/main.css _nemazat/css/main.css
_nemazat/css/font-awesome.min.css _nemazat/css/font-awesome.min.css
app/logs/*.log app/logs/*.log
.vscode/
.vscode/sftp.json
app/updater/*.bin

View File

@@ -12,6 +12,7 @@ RewriteRule (.*) index.php?url=$1 [QSA,L]
RewriteCond %{HTTPS} off RewriteCond %{HTTPS} off
RewriteCond %{REQUEST_FILENAME} !api.php RewriteCond %{REQUEST_FILENAME} !api.php
RewriteCond %{REQUEST_FILENAME} !apiFront.php
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301] RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
AddType application/x-httpd-php .php .phtml AddType application/x-httpd-php .php .phtml

13
.todo Normal file
View File

@@ -0,0 +1,13 @@
//TODO: Automation last Run Time
//TODO: Check if every automation type Works
//TODO: Add Switch to Setting For debug mode
//TODO: hide menu item Debug When Debug mode is disabled
//TODO: Check if every setting works
//TODO: Add slector to automation execute all To execute only utomation whitch contain same day (as actual to speed up process)
//TODO: Check and fix time based automation
//TODO: 404 same like in ENergo COunter Project
//TODO: @FILIP Fix Editation of all Automations
//TODO: @FILIP test if registration work without an isuu even with notification
//TODO: Fix Default Room selection
//TODO: Fix User Delete button
//TODO: Fix new add email form

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,88 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <ArduinoJson.h>
//USER CONFIGURATION
const char* WIFI_SSID = "";
const char* WIFI_PASS = "";
const char* HW_TOKEN = "";
const char* SERVER_ADRESS = "";
StaticJsonDocument<250> jsonBuffer;
String requestJson = "";
ADC_MODE(ADC_VCC);
//Pins
#define SENZORPIN 12 //12
void setup() {
Serial.begin(9600);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(WIFI_SSID, WIFI_PASS);
checkConnection();
Serial.print("TEST");
jsonBuffer = {};
jsonBuffer["token"] = HW_TOKEN;
jsonBuffer["values"]["door"]["value"] = 0;
int batteryVoltage = (ESP.getVcc() + 600) / 1000;
jsonBuffer["values"]["battery"]["value"] = batteryVoltage;
serializeJson(jsonBuffer, requestJson);
sendHttpRequest(requestJson);
delay(500);
ESP.deepSleep(0);
}
void loop() {
}
void setStaticIp(String ipAddress, String subnet, String gateway){
//Set static ip
IPAddress staticIpAddress;
IPAddress subnetIpAddress;
IPAddress gatewayIpAddress;
if (
staticIpAddress.fromString(ipAddress) &&
subnetIpAddress.fromString(subnet) &&
gatewayIpAddress.fromString(gateway) &&
WiFi.localIP() != staticIpAddress
) {
WiFi.config(staticIpAddress, subnetIpAddress, gatewayIpAddress);
Serial.print("STATIC IP address:");
Serial.println(WiFi.localIP());
}
}
String sendHttpRequest (String requestJson) {
HTTPClient http;
http.setReuse(true);
http.begin(SERVER_ADRESS);
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
if (httpCode == -1) {
ESP.restart();
}
return payload;
}
bool checkConnection() {
int count = 0;
while ( count < 30 ) {
delay(500);
if (WiFi.status() == WL_CONNECTED) {
return true;
}
count++;
}
return false;
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 44 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

View File

@@ -0,0 +1,153 @@
//Includes
#include <DHT.h>
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <ArduinoJson.h>
//Variables
const char* ssid = "Smart-Home";
const char* pasw = "S1pjg3684dcCPTUQ";
const char* hwId = "45235sadad";
const char* url = "http://dev.steelants.cz/vasek/home/api.php";
int unsuccessfulRounds = 0;
//Pins
#define pinDHT 4
#define LIGHTPIN 13
//Inicializations
DHT DHTs(pinDHT, DHT11);
void setup() {
Serial.begin(9600);
while (!Serial) continue;
delay(10);
Serial.println('\n');
//Show start up Configuration
Serial.println("HW: " + String(hwId));
Serial.print("IP address:\t");
Serial.println(WiFi.localIP());
Serial.print("MAC address:\t");
Serial.println(WiFi.macAddress());
pinMode(LIGHTPIN, INPUT);
}
void loop() {
//Start Conection to wifi
WiFi.begin(ssid, pasw);
checkConnection();
//HTTP CLIENT
HTTPClient http;
http.begin(url); //Begun HTTP Request
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
DHTs.begin();
//JsonDocsDefinition
StaticJsonDocument<265> doc;
doc["token"] = hwId;
//Read and Handle DHT values
float tem = DHTs.readTemperature();
float hum = DHTs.readHumidity();
Serial.println("TEMP" + String(tem) + ";HUMI" + String(hum));
if (isnan(tem) || isnan(hum)) {
Serial.println("Unable to read DHT");
} else {
doc["values"]["temp"]["value"] = tem;
doc["values"]["temp"]["unit"] = "C";
doc["values"]["humi"]["value"] = hum;
doc["values"]["humi"]["unit"] = "%";
}
//Handle Photo Rezistor Values
doc["values"]["light"]["value"] = (String)!digitalRead(LIGHTPIN);
doc["values"]["light"]["unit"] = "";
/*More Senzores to come*/
String jsonPayload = "";
serializeJson(doc, jsonPayload);
Serial.print("JSON: ");
Serial.println(jsonPayload);
int httpCode = http.POST(jsonPayload); //Get Http response code
String httpPayload = http.getString(); //Get the response payload
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(httpPayload) + ""); //Print request response payload
DeserializationError error = deserializeJson(doc, httpPayload); //Get deserialization Error if exists
//configuration setup
int sleepTime = doc["device"]["sleepTime"];
String hostName = doc["device"]["hostname"];
String ipAddress = doc["device"]["ipAddress"];
String gateway = doc["device"]["gateway"];
String subnet = doc["device"]["subnet"];
String state = doc["state"];
if (state != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + (String)unsuccessfulRounds + "FROM 5");
} else if (state == "succes") {
unsuccessfulRounds = 0;
}
//Set static ip
setStaticIp(ipAddress, gateway, subnet);
WiFi.hostname(hostName); //Set HostName
http.end(); //Close connection
WiFi.disconnect(); //Disconect from WIFI
Serial.println("DISCONECTED FROM WIFI");
if(unsuccessfulRounds == 5) { //after 5 unsucessful request restart ESP
Serial.println("RESTARTING ESP");
ESP.restart();
}
sleep(sleepTime);
}
//checking if connection is working
bool checkConnection() {
int count = 0;
Serial.print("Waiting for Wi-Fi connection");
while ( count < 30 ) {
if (WiFi.status() == WL_CONNECTED) {
Serial.println();
Serial.println("Connected!");
return (true);
}
delay(500);
Serial.print(".");
count++;
}
Serial.println("Timed out.");
return false;
}
void setStaticIp(String IpAddress, String subnet, String gateway){
//Set static ip
IPAddress staticIpAddress;
IPAddress subnetIpAddress;
IPAddress gatewayIpAddress;
if (
staticIpAddress.fromString(IpAddress) &&
subnetIpAddress.fromString(subnet) &&
gatewayIpAddress.fromString(gateway) &&
WiFi.localIP() != staticIpAddress
) {
WiFi.config(staticIpAddress, subnetIpAddress, gatewayIpAddress);
Serial.print("STATIC IP address:\t");
Serial.println(WiFi.localIP());
}
}
void sleep(int sleepTime) {
if (sleepTime > 0) { //if deep sleepTime > 0 use deep sleep
Serial.println("GOING TO SLEEP FOR " + String(sleepTime));
ESP.deepSleep((sleepTime * 60) * 1000000, RF_DEFAULT);
} else {
delay(5000);
}
}

View File

@@ -0,0 +1,387 @@
//Includes
#include <DHT.h>
#include <ESP8266WiFi.h>
#include <ESP8266WebServer.h>
#include <WiFiClientSecure.h>
#include <ESP8266HTTPClient.h>
#define ARDUINOJSON_DECODE_UNICODE 1
#include <ArduinoJson.h>
#include <EEPROM.h>
#include "ESP8266httpUpdate.h"
//Variables
const char* ssidServer = "";
const char* paswServer = "";
String ssid = "";
String pasw = "";
String apiToken = "";
const int httpsPort = 443;
const char* host = "http://dev.steelants.cz";
const char* url = "/vasek/home/api.php";
const char* fingerprint = "";
const char* host2 = "dev.steelants.cz";
const char* url2 = "/vasek/home/update.php";
String content;
String Logs;
bool conf = false;
bool buttonActive = false;
int state = 0;
String requestJson = "";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
ESP8266WebServer server(80);
StaticJsonDocument<265> jsonContent;
DeserializationError error;
//Pins
#define DHTPIN 2
//#define LIGHTPIN 13
//Inicializations
DHT DHTs(DHTPIN, DHT11);
void setup() {
Serial.begin(9600);
EEPROM.begin(100);
while (!Serial) continue;
delay(10);
//read saved data
ssid = ReadEeprom(1, 33);
pasw = ReadEeprom(33, 65);
apiToken = ReadEeprom(65, 97);
#if defined(LIGHTPIN)
//set pins
pinMode(LIGHTPIN, INPUT);
#endif
//wifi
if (ssid != "") {
WiFi.disconnect();
WiFi.softAPdisconnect(true);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
conf = wifiVerify(20);
if (conf) {
configTime(3 * 3600, 0, "pool.ntp.org");
WiFiClientSecure client;
Serial.print("connecting to ");
Serial.println(host2);
client.setInsecure();
if (!client.connect(host2, httpsPort)) {
addLog("connection failed");
Serial.println("connection failed");
return;
}
if (client.verify(fingerprint, host2)) {
Serial.println("certificate matches");
} else {
addLog("certificate doesn't match");
Serial.println("certificate doesn't match");
return;
}
Serial.print("Starting OTA from: ");
Serial.println(url2
);
auto ret = ESPhttpUpdate.update(client, host2, 80, url2);
delay(500);
switch(ret) {
case HTTP_UPDATE_FAILED:
addLog("HTTP_UPDATE_FAILD Error (" + (String)ESPhttpUpdate.getLastError() + ") : " + (String)ESPhttpUpdate.getLastErrorString().c_str());
Serial.printf("HTTP_UPDATE_FAILD Error (%d): %s", ESPhttpUpdate.getLastError(), ESPhttpUpdate.getLastErrorString().c_str());
Serial.println();
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_NO_UPDATES:
Serial.println("HTTP_UPDATE_NO_UPDATES");
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_OK:
Serial.println("HTTP_UPDATE_OK");
Serial.println();
Serial.println();
Serial.println();
break;
}
delay(500);
jsonContent = {};
jsonContent["token"] = apiToken;
jsonContent["settings"]["network"]["ip"] = WiFi.localIP().toString();
jsonContent["settings"]["network"]["mac"] = WiFi.macAddress();
jsonContent["settings"]["firmware_hash"] = ESP.getSketchMD5();
sendDataToWeb();
return;
}
}
setupAP();
}
void loop() {
if (conf) {
LogErrors();
if (unsuccessfulRounds >= 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
DHTs.begin();
jsonContent = {};
jsonContent["token"] = apiToken;
requestJson = "";
//Read and Handle DHT values
float tem = DHTs.readTemperature();
float hum = DHTs.readHumidity();
Serial.println("TEMP" + String(tem) + ";HUMI" + String(hum));
if (isnan(tem) || isnan(hum)) {
Serial.println("Unable to read DHT");
} else {
jsonContent["values"]["temp"]["value"] = (String)tem;
jsonContent["values"]["temp"]["unit"] = "C";
jsonContent["values"]["humi"]["value"] = (String)hum;
jsonContent["values"]["humi"]["unit"] = "%";
}
#if defined(LIGHTPIN)
//Handle Photo Rezistor Values
jsonContent["values"]["light"]["value"] = (String)!digitalRead(LIGHTPIN);
jsonContent["values"]["light"]["unit"] = "";
#endif
sendDataToWeb();
loadDataFromWeb();
} else {
server.handleClient();
}
}
bool wifiVerify(int t) {
int c = 0;
Serial.println("Waiting for Wifi");
while (c < t) {
if (WiFi.status() == WL_CONNECTED) {
c = t;
return true;
}
delay(500);
Serial.print(WiFi.status());
c++;
}
return false;
}
void loadDataFromWeb() {
if (error.code() != DeserializationError::Ok) {
addLog(error.c_str());
Serial.println(error.c_str());
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
error = DeserializationError::Ok;
return;
}
//configuration setup
int sleepTime = jsonContent["device"]["sleepTime"];
String hostName = jsonContent["device"]["hostname"];
String requestState = jsonContent["state"];
String command = jsonContent["command"];
if (command == "reset"){
command = "";
ESP.reset();
} else if (command == "config") {
command = "";
CleanEeprom();
EEPROM.commit();
ESP.restart();
}
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
WiFi.hostname(hostName);
sleep(sleepTime);
}
void sendDataToWeb() {
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
error = deserializeJson(jsonContent, sendHttpRequest());
}
void sleep(int sleepTime) {
if (sleepTime > 0) { //if deep sleepTime > 0 use deep sleep
Serial.println("GOING TO SLEEP FOR " + String(sleepTime));
ESP.deepSleep((sleepTime * 60) * 1000000, RF_DEFAULT);
} else {
delay(5000);
}
}
String sendHttpRequest () {
HTTPClient http;
http.setReuse(true);
Serial.println("HTTP url: " + String(host) + String(url) + ""); //Print HTTP return code
http.begin(String(host) + String(url));
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
Serial.println("HTTP request: " + String(requestJson) + ""); //Print HTTP return code
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
if (httpCode == -1) {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return "";
}
return payload;
}
void LogErrors() {
jsonContent = {};
error = deserializeJson(jsonContent, "{\"logs\":[" + Logs + "]}");
jsonContent["token"] = apiToken;
requestJson = "";
Logs = "";
sendDataToWeb();
}
void addLog(String logText) {
if (Logs == "") {
Logs = "\"" + logText + "\"";
} else {
Logs += ",\"" + logText + "\"";
}
}
void CleanEeprom() {
for (int i = 1; i < 100; ++i) {
EEPROM.write(i, 0);
}
}
void WriteEeprom (String data, int start = 1) {
for (int i = 0; i < data.length(); ++i)
{
EEPROM.write(start + i, data[i]);
}
EEPROM.commit();
}
String ReadEeprom(int min, int max) {
String localString;
for (int i = min; i < max; ++i) {
localString += char(EEPROM.read(i));
}
return localString;
}
void createWeb()
{
server.on("/", []() {
if (server.args() == 3) {
ssid = server.arg("wifi-ssid");
pasw = server.arg("wifi-pasw");
apiToken = server.arg("apiToken");
if (ssid != "" && pasw != "" && apiToken != "") {
CleanEeprom();
WriteEeprom(ssid);
WriteEeprom(pasw, 33);
WriteEeprom(apiToken, 65);
server.send(200, "application/json", "Restarting esp");
delay(500);
ESP.restart();
}
}
content = "<!DOCTYPE HTML><body>";
content += "<head><style>";
content += "html,body {height: 100%;}";
content += "html {display: table;margin: auto;}";
content += "body {display: table-cell;vertical-align: middle;}";
content += "input {width: 100%;box-sizing: border-box}";
content += "</style></head>";
content += "<h2>WIFI Configuration</h2>";
content += "<h4><b>" + (String)ssidServer + "</b></h4>";
content += "<a href='#'>Refresh</a>";
content += "<div class=\"wifi-list\">";
int n = WiFi.scanNetworks();
if (n == 0)
content += "<label>No networks found...</label>";
else
{
for (int i = 0; i < n; ++i)
{
content += "<a href=\"#\" onclick=\"fillSSID(this.innerHTML)\">" + WiFi.SSID(i) + "</a><br>";
}
}
content += "</div>";
content += "<form method='get' action=''><div class='wifi-form'>";
content += "<label>SSID: </label><input name='wifi-ssid' id='wifi-ssid' length=32 type='text'><br>";
content += "<label>Heslo: </label><input name='wifi-pasw' length=32 type='password'><br>";
content += "<label>Api token: </label><input name='apiToken' length=32 type='password'><br>";
content += "<input type='submit' value='Connect'>";
content += "</div></form>";
content += "<script>";
content += "function fillSSID(value) {\r\n";
content += "document.getElementById(\"wifi-ssid\").value = value;\r\n";
content += "}";
content += "</script>";
content += "</body>";
server.send(200, "text/html", content);
});
}
void setupAP(void) {
WiFi.mode(WIFI_STA);
WiFi.disconnect();
WiFi.softAPdisconnect(true);
delay(100);
int n = WiFi.scanNetworks();
Serial.println("scan done");
if (n == 0)
Serial.println("no networks found");
else
{
Serial.print(n);
Serial.println(" networks found");
for (int i = 0; i < n; ++i)
{
// Print SSID and RSSI for each network found
Serial.print(i + 1);
Serial.print(": ");
Serial.print(WiFi.SSID(i));
Serial.print(" (");
Serial.print(WiFi.RSSI(i));
Serial.print(")");
Serial.println((WiFi.encryptionType(i) == ENC_TYPE_NONE) ? " " : "*");
delay(10);
}
}
delay(100);
WiFi.softAP(ssidServer, paswServer);
Serial.println("softap");
Serial.println("");
Serial.println("WiFi connected");
Serial.print("Local IP: ");
Serial.println(WiFi.localIP());
Serial.print("SoftAP IP: ");
Serial.println(WiFi.softAPIP());
createWeb();
// Start the server
server.begin();
Serial.println("Server started");
Serial.println("over");
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 KiB

View File

@@ -0,0 +1,206 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <ArduinoJson.h>
#include <EEPROM.h>
//Variables
const char* ssid = "ssid";
const char* pasw = "pasw";
const char* hwId = "hwId";
const char* server = "http://dev.steelants.cz/vasek/home/api.php";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
StaticJsonDocument<250> jsonContent;
bool buttonActive = false;
int interuptCount = 0;
int realState = 0;
int state = 0;
String requestJson = "";
//Pins
#define RELAY 4 //12
#define SWITCH 5 //0
void ICACHE_RAM_ATTR handleInterrupt ();
void setup() {
Serial.begin(9600);
EEPROM.begin(1);
while (!Serial) continue;
delay(10);
Serial.println('\n');
Serial.println("HW: " + String(hwId));
pinMode(SWITCH, INPUT);
pinMode(RELAY, OUTPUT);
state = EEPROM.read(0);
digitalWrite(RELAY, state);
realState = state;
attachInterrupt(digitalPinToInterrupt(SWITCH), handleInterrupt, CHANGE);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
checkConnection();
Serial.println('\n');
Serial.println("Connection established!");
Serial.print("IP address:");
Serial.println(WiFi.localIP());
Serial.print("MAC address:");
Serial.println(WiFi.macAddress());
jsonContent = {};
jsonContent["token"] = hwId;
jsonContent["values"]["on/off"]["value"] = (String)realState;
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
}
void loop() {
if(unsuccessfulRounds >= 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
jsonContent = {};
jsonContent["token"] = hwId;
requestJson = "";
if (buttonActive){
int realStateLocal = digitalRead(SWITCH);
jsonContent["values"]["on/off"]["value"] = (String)realStateLocal;
digitalWrite(RELAY, realStateLocal);
realState = realStateLocal;
EEPROM.write(0, realState);
EEPROM.commit();
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
//HTTP CLIENT
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
buttonActive = false;
}
jsonContent = {};
jsonContent["token"] = hwId;
requestJson = "";
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
//HTTP CLIENT
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
if (error) {
Serial.println(error.c_str());
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return;
}
//configuration setup
String hostName = jsonContent["device"]["hostname"];
String ipAddress = jsonContent["device"]["ipAddress"];
String gateway = jsonContent["device"]["gateway"];
String subnet = jsonContent["device"]["subnet"];
String requestState = jsonContent["state"];
JsonObject object = jsonContent.as<JsonObject>();
if (!object["value"].isNull()) {
state = (int)jsonContent["value"];
}
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
//Set static ip
setStaticIp(ipAddress, gateway, subnet);
WiFi.hostname(hostName);
Serial.println("state: " + (String)state + ", realState: " + (String)realState);
if (state != realState){
if (state == 1 && realState == 0) {
Serial.println("ON state: " + (String)state + ", realState: " + (String)realState);
digitalWrite(RELAY, HIGH); // Turn the LED on by making the voltage LOW
realState = 1;
} else {
Serial.println("OFF");
digitalWrite(RELAY, LOW); // Turn the LED on by making the voltage LOW
realState = 0;
}
EEPROM.write(0, realState);
EEPROM.commit();
}
}
void handleInterrupt() {
interuptCount++;
buttonActive = true;
}
String sendHttpRequest (String requestJson) {
HTTPClient http;
http.setReuse(true);
http.begin(server);
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
if (httpCode == -1) {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return "";
}
return payload;
}
bool checkConnection() {
int count = 0;
Serial.print("Waiting for Wi-Fi connection");
while ( count < 30 ) {
if (buttonActive){
int realStateLocal = digitalRead(SWITCH);
digitalWrite(RELAY, realStateLocal);
realState = realStateLocal;
EEPROM.write(0, realState);
EEPROM.commit();
buttonActive = false;
}
delay(250);
if (WiFi.status() == WL_CONNECTED) {
Serial.println();
Serial.println("Connected!");
return (true);
}
Serial.print(".");
count++;
}
Serial.println("Timed out.");
return false;
}
void setStaticIp(String ipAddress, String subnet, String gateway){
//Set static ip
IPAddress staticIpAddress;
IPAddress subnetIpAddress;
IPAddress gatewayIpAddress;
if (
staticIpAddress.fromString(ipAddress) &&
subnetIpAddress.fromString(subnet) &&
gatewayIpAddress.fromString(gateway) &&
WiFi.localIP() != staticIpAddress
) {
WiFi.config(staticIpAddress, subnetIpAddress, gatewayIpAddress);
Serial.print("STATIC IP address:");
Serial.println(WiFi.localIP());
}
}

View File

@@ -0,0 +1,360 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266WebServer.h>
#include <WiFiClientSecure.h>
#include <ESP8266HTTPClient.h>
#define ARDUINOJSON_DECODE_UNICODE 1
#include <ArduinoJson.h>
#include <EEPROM.h>
#include "ESP8266httpUpdate.h"
//Variables
const char* ssidServer = "";
const char* paswServer = "";
String ssid = "";
String pasw = "";
String apiToken = "";
const int httpsPort = 443;
const char* host = "http://dev.steelants.cz";
const char* url = "/vasek/home/api.php";
const char* fingerprint = "";
const char* host2 = "dev.steelants.cz";
const char* url2 = "/vasek/home/update.php";
String content;
bool conf = false;
bool buttonActive = false;
int state = 0;
String requestJson = "";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
ESP8266WebServer server(80);
StaticJsonDocument<250> jsonContent;
DeserializationError error;
//Pins
#define RELAY 4 //12
#define SWITCH 5 //0
void ICACHE_RAM_ATTR handleInterrupt ();
void setup() {
Serial.begin(115200);
EEPROM.begin(100);
while (!Serial) continue;
delay(10);
//read saved data
ssid = ReadEeprom(1, 33);
pasw = ReadEeprom(33, 65);
apiToken = ReadEeprom(65, 97);
//set pins
pinMode(SWITCH, INPUT);
pinMode(RELAY, OUTPUT);
state = EEPROM.read(0);
digitalWrite(RELAY, state);
attachInterrupt(digitalPinToInterrupt(SWITCH), handleInterrupt, CHANGE);
//wifi
if (ssid != "") {
WiFi.disconnect();
WiFi.softAPdisconnect(true);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
conf = wifiVerify(20);
if (conf) {
configTime(3 * 3600, 0, "pool.ntp.org");
WiFiClientSecure client;
Serial.print("connecting to ");
Serial.println(host2);
client.setInsecure();
if (!client.connect(host2, httpsPort)) {
Serial.println("connection failed");
return;
}
if (client.verify(fingerprint, host2)) {
Serial.println("certificate matches");
} else {
Serial.println("certificate doesn't match");
return;
}
Serial.print("Starting OTA from: ");
Serial.println(url2
);
auto ret = ESPhttpUpdate.update(client, host2, 80, url2);
delay(500);
switch(ret) {
case HTTP_UPDATE_FAILED:
Serial.printf("HTTP_UPDATE_FAILD Error (%d): %s", ESPhttpUpdate.getLastError(), ESPhttpUpdate.getLastErrorString().c_str());
Serial.println();
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_NO_UPDATES:
Serial.println("HTTP_UPDATE_NO_UPDATES");
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_OK:
Serial.println("HTTP_UPDATE_OK");
Serial.println();
Serial.println();
Serial.println();
break;
}
delay(500);
jsonContent = {};
jsonContent["token"] = apiToken;
jsonContent["values"]["on/off"]["value"] = (String)state;
jsonContent["settings"]["network"]["ip"] = WiFi.localIP().toString();
jsonContent["settings"]["network"]["mac"] = WiFi.macAddress();
jsonContent["settings"]["firmware_hash"] = ESP.getSketchMD5();
sendDataToWeb();
return;
}
}
setupAP();
}
void loop() {
if (conf) {
if (unsuccessfulRounds >= 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
if (buttonActive) {
jsonContent = {};
jsonContent["token"] = apiToken;
requestJson = "";
jsonContent["values"]["on/off"]["value"] = (String)state;
digitalWrite(RELAY, state);
EEPROM.write(0, state);
EEPROM.commit();
sendDataToWeb();
buttonActive = false;
delay(500);
} else {
loadDataFromWeb();
}
} else {
server.handleClient();
}
}
void handleInterrupt() {
buttonActive = true;
state = !state;
digitalWrite(RELAY, state);
}
bool wifiVerify(int t) {
int c = 0;
Serial.println("Waiting for Wifi to connect to Shelly1");
while (c < t) {
if (WiFi.status() == WL_CONNECTED) {
c = t;
return true;
}
delay(500);
Serial.print(WiFi.status());
c++;
}
return false;
}
void loadDataFromWeb() {
jsonContent = {};
jsonContent["token"] = apiToken;
requestJson = "";
sendDataToWeb();
if (error.code() != DeserializationError::Ok) {
Serial.println(error.c_str());
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
error = DeserializationError::Ok;
return;
}
//configuration setup
String hostName = jsonContent["device"]["hostname"];
String requestState = jsonContent["state"];
String command = jsonContent["command"];
if (!buttonActive) {
state = (int)jsonContent["value"];
Serial.println("state: " + (String)state);
digitalWrite(RELAY, state);
EEPROM.write(0, state);
EEPROM.commit();
delay(500);
}
if (command == "reset"){
ESP.reset();
} else if (command == "config") {
CleanEeprom();
EEPROM.commit();
ESP.restart();
}
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
WiFi.hostname(hostName);
}
void sendDataToWeb() {
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
error = deserializeJson(jsonContent, sendHttpRequest());
}
String sendHttpRequest () {
HTTPClient http;
http.setReuse(true);
Serial.println("HTTP url: " + String(host) + String(url) + ""); //Print HTTP return code
http.begin(String(host) + String(url));
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
Serial.println("HTTP request: " + String(requestJson) + ""); //Print HTTP return code
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
if (httpCode == -1) {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return "";
}
return payload;
}
void CleanEeprom() {
for (int i = 1; i < 100; ++i) {
EEPROM.write(i, 0);
}
}
void WriteEeprom (String data, int start = 1) {
for (int i = 0; i < data.length(); ++i)
{
EEPROM.write(start + i, data[i]);
}
EEPROM.commit();
}
String ReadEeprom(int min, int max) {
String localString;
for (int i = min; i < max; ++i) {
localString += char(EEPROM.read(i));
}
return localString;
}
void createWeb()
{
server.on("/", []() {
if (server.args() == 3) {
ssid = server.arg("wifi-ssid");
pasw = server.arg("wifi-pasw");
apiToken = server.arg("apiToken");
if (ssid != "" && pasw != "" && apiToken != "") {
CleanEeprom();
WriteEeprom(ssid);
WriteEeprom(pasw, 33);
WriteEeprom(apiToken, 65);
server.send(200, "application/json", "Restarting esp");
delay(500);
ESP.restart();
}
}
content = "<!DOCTYPE HTML><body>";
content += "<head><style>";
content += "html,body {height: 100%;}";
content += "html {display: table;margin: auto;}";
content += "body {display: table-cell;vertical-align: middle;}";
content += "input {width: 100%;box-sizing: border-box}";
content += "</style></head>";
content += "<h2>WIFI Configuration</h2>";
content += "<a href='#'>Refresh</a>";
content += "<div class=\"wifi-list\">";
int n = WiFi.scanNetworks();
if (n == 0)
content += "<label>No networks found...</label>";
else
{
for (int i = 0; i < n; ++i)
{
content += "<a href=\"#\" onclick=\"fillSSID(this.innerHTML)\">" + WiFi.SSID(i) + "</a><br>";
}
}
content += "</div>";
content += "<form method='get' action=''><div class='wifi-form'>";
content += "<label>SSID: </label><input name='wifi-ssid' id='wifi-ssid' length=32 type='text'><br>";
content += "<label>Heslo: </label><input name='wifi-pasw' length=32 type='password'><br>";
content += "<label>Api token: </label><input name='apiToken' length=32 type='password'><br>";
content += "<input type='submit' value='Connect'>";
content += "</div></form>";
content += "<script>";
content += "function fillSSID(value) {\r\n";
content += "document.getElementById(\"wifi-ssid\").value = value;\r\n";
content += "}";
content += "</script>";
content += "</body>";
server.send(200, "text/html", content);
});
}
void setupAP(void) {
WiFi.mode(WIFI_STA);
WiFi.disconnect();
WiFi.softAPdisconnect(true);
delay(100);
int n = WiFi.scanNetworks();
Serial.println("scan done");
if (n == 0)
Serial.println("no networks found");
else
{
Serial.print(n);
Serial.println(" networks found");
for (int i = 0; i < n; ++i)
{
// Print SSID and RSSI for each network found
Serial.print(i + 1);
Serial.print(": ");
Serial.print(WiFi.SSID(i));
Serial.print(" (");
Serial.print(WiFi.RSSI(i));
Serial.print(")");
Serial.println((WiFi.encryptionType(i) == ENC_TYPE_NONE) ? " " : "*");
delay(10);
}
}
delay(100);
WiFi.softAP(ssidServer, paswServer);
Serial.println("softap");
Serial.println("");
Serial.println("WiFi connected");
Serial.print("Local IP: ");
Serial.println(WiFi.localIP());
Serial.print("SoftAP IP: ");
Serial.println(WiFi.softAPIP());
createWeb();
// Start the server
server.begin();
Serial.println("Server started");
Serial.println("over");
}

Binary file not shown.

After

Width:  |  Height:  |  Size: 19 KiB

View File

@@ -0,0 +1,221 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <ArduinoJson.h>
#include <EEPROM.h>
//Variables
const char* ssid = "Smart-Home";
const char* pasw = "S1pjg3684dcCPTUQ";
const char* hwId = "452r5s8dad";
const char* server = "http://dev.steelants.cz/vasek/home/api.php";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
StaticJsonDocument<250> jsonContent;
bool buttonActive = false;
int interuptCount = 0;
int realState = 1;
int state = 0;
String requestJson = "";
//Pins
#define SONOFF 12 //12
#define SONOFF_LED 13
#define SONOFF_BUT 0 //0
void ICACHE_RAM_ATTR handleInterrupt ();
void setup() {
Serial.begin(9600);
EEPROM.begin(1);
while (!Serial) continue;
delay(10);
Serial.println('\n');
Serial.println("HW: " + String(hwId));
pinMode(SONOFF_LED, OUTPUT);
pinMode(SONOFF_BUT, INPUT_PULLUP);
pinMode(SONOFF, OUTPUT);
state = EEPROM.read(0);
digitalWrite(SONOFF, state);
realState = state;
attachInterrupt(digitalPinToInterrupt(SONOFF_BUT), handleInterrupt, FALLING);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
checkConnection();
Serial.println('\n');
Serial.println("Connection established!");
Serial.print("IP address:");
Serial.println(WiFi.localIP());
Serial.print("MAC address:");
Serial.println(WiFi.macAddress());
jsonContent = {};
jsonContent["token"] = hwId;
jsonContent["values"]["on/off"]["value"] = (String)realState;
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
}
void loop() {
if(unsuccessfulRounds >= 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
jsonContent = {};
jsonContent["token"] = hwId;
requestJson = "";
if (buttonActive == true){
jsonContent["values"]["on/off"]["value"] = (String)!realState;
if (!realState == 1) {
digitalWrite(SONOFF, HIGH);
realState = 1;
} else if (!realState == 0){
digitalWrite(SONOFF, LOW);
realState = 0;
}
EEPROM.write(0, 0);
EEPROM.commit();
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
//HTTP CLIENT
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
buttonActive = false;
}
jsonContent = {};
jsonContent["token"] = hwId;
requestJson = "";
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
//HTTP CLIENT
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
if (error) {
Serial.println(error.c_str());
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return;
}
//configuration setup
String hostName = jsonContent["device"]["hostname"];
String ipAddress = jsonContent["device"]["ipAddress"];
String gateway = jsonContent["device"]["gateway"];
String subnet = jsonContent["device"]["subnet"];
String requestState = jsonContent["state"];
JsonObject object = jsonContent.as<JsonObject>();
if (!object["value"].isNull()) {
state = (int)jsonContent["value"];
}
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
//Set static ip
setStaticIp(ipAddress, gateway, subnet);
WiFi.hostname(hostName);
Serial.println("state: " + (String)state + ", realState: " + (String)realState);
if (state != realState){
if (state == 1 && realState == 0) {
Serial.println("ON state: " + (String)state + ", realState: " + (String)realState);
digitalWrite(SONOFF, HIGH); // Turn the LED on by making the voltage LOW
realState = 1;
} else if (state == 0 && realState == 1) {
Serial.println("OFF");
digitalWrite(SONOFF, LOW); // Turn the LED on by making the voltage LOW
realState = 0;
}
EEPROM.write(0, realState);
EEPROM.commit();
}
}
void handleInterrupt() {
interuptCount++;
buttonActive = true;
}
String sendHttpRequest (String requestJson) {
HTTPClient http;
http.setReuse(true);
http.begin(server);
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
if (httpCode == -1) {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return "";
}
return payload;
}
bool checkConnection() {
int count = 0;
Serial.print("Waiting for Wi-Fi connection");
while ( count < 30 ) {
if (buttonActive == true){
if (!realState == 1) {
digitalWrite(SONOFF, HIGH);
realState = 1;
} else if (!realState == 0){
digitalWrite(SONOFF, LOW);
realState = 0;
}
EEPROM.write(0, realState);
EEPROM.commit();
buttonActive = false;
}
digitalWrite(SONOFF_LED, HIGH);
delay(125);
digitalWrite(SONOFF_LED, LOW);
delay(125);
if (WiFi.status() == WL_CONNECTED) {
Serial.println();
Serial.println("Connected!");
digitalWrite(SONOFF_LED, HIGH);
return (true);
}
Serial.print(".");
count++;
}
Serial.println("Timed out.");
return false;
}
void setStaticIp(String ipAddress, String subnet, String gateway){
//Set static ip
IPAddress staticIpAddress;
IPAddress subnetIpAddress;
IPAddress gatewayIpAddress;
if (
staticIpAddress.fromString(ipAddress) &&
subnetIpAddress.fromString(subnet) &&
gatewayIpAddress.fromString(gateway) &&
WiFi.localIP() != staticIpAddress
) {
WiFi.config(staticIpAddress, subnetIpAddress, gatewayIpAddress);
Serial.print("STATIC IP address:");
Serial.println(WiFi.localIP());
}
}

View File

@@ -0,0 +1,373 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266WebServer.h>
#include <WiFiClientSecure.h>
#include <ESP8266HTTPClient.h>
#define ARDUINOJSON_DECODE_UNICODE 1
#include <ArduinoJson.h>
#include <EEPROM.h>
#include "ESP8266httpUpdate.h"
//Variables
const char* ssidServer = "";
const char* paswServer = "";
String ssid = "";
String pasw = "";
String apiToken = "";
const int httpsPort = 443;
const char* host = "http://dev.steelants.cz";
const char* url = "/vasek/home/api.php";
const char* fingerprint = "";
const char* host2 = "dev.steelants.cz";
const char* url2 = "/vasek/home/update.php";
String content;
bool conf = false;
bool buttonActive = false;
int state = 0;
String requestJson = "";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
ESP8266WebServer server(80);
StaticJsonDocument<250> jsonContent;
DeserializationError error;
//Pins
#define SONOFF 12
#define SONOFF_LED 13
#define SONOFF_BUT 0 //0
void ICACHE_RAM_ATTR handleInterrupt ();
void setup() {
Serial.begin(9600);
EEPROM.begin(100);
while (!Serial) continue;
delay(10);
//read saved data
ssid = ReadEeprom(1, 33);
pasw = ReadEeprom(33, 65);
apiToken = ReadEeprom(65, 97);
//set pins
pinMode(SONOFF_LED, OUTPUT);
pinMode(SONOFF_BUT, INPUT_PULLUP);
pinMode(SONOFF, OUTPUT);
state = EEPROM.read(0);
digitalWrite(SONOFF, state);
attachInterrupt(digitalPinToInterrupt(SONOFF_BUT), handleInterrupt, FALLING);
//wifi
if (ssid != "") {
WiFi.disconnect();
WiFi.softAPdisconnect(true);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
conf = wifiVerify(20);
if (conf) {
configTime(3 * 3600, 0, "pool.ntp.org");
WiFiClientSecure client;
Serial.print("connecting to ");
Serial.println(host2);
client.setInsecure();
if (!client.connect(host2, httpsPort)) {
Serial.println("connection failed");
return;
}
if (client.verify(fingerprint, host2)) {
Serial.println("certificate matches");
} else {
Serial.println("certificate doesn't match");
return;
}
Serial.print("Starting OTA from: ");
Serial.println(url2
);
auto ret = ESPhttpUpdate.update(client, host2, 80, url2);
delay(500);
switch(ret) {
case HTTP_UPDATE_FAILED:
Serial.printf("HTTP_UPDATE_FAILD Error (%d): %s", ESPhttpUpdate.getLastError(), ESPhttpUpdate.getLastErrorString().c_str());
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_NO_UPDATES:
Serial.println("HTTP_UPDATE_NO_UPDATES");
Serial.println();
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_OK:
Serial.println("HTTP_UPDATE_OK");
Serial.println();
Serial.println();
break;
}
delay(500);
jsonContent = {};
jsonContent["token"] = apiToken;
jsonContent["values"]["on/off"]["value"] = (String)state;
jsonContent["settings"]["network"]["ip"] = WiFi.localIP().toString();
jsonContent["settings"]["network"]["mac"] = WiFi.macAddress();
jsonContent["settings"]["firmware_hash"] = ESP.getSketchMD5();
sendDataToWeb();
return;
}
}
setupAP();
}
void loop() {
if (conf) {
if (unsuccessfulRounds >= 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
jsonContent = {};
jsonContent["token"] = apiToken;
requestJson = "";
if (buttonActive) {
jsonContent["values"]["on/off"]["value"] = (String)state;
digitalWrite(SONOFF, state);
EEPROM.write(0, state);
EEPROM.commit();
sendDataToWeb();
buttonActive = false;
delay(500);
} else {
sendDataToWeb();
loadDataFromWeb();
}
} else {
server.handleClient();
}
}
void handleInterrupt() {
buttonActive = true;
state = !state;
digitalWrite(SONOFF, state);
}
bool wifiVerify(int t) {
int c = 0;
Serial.println("Waiting for Wifi to connect to Shelly1");
while (c < t) {
if (WiFi.status() == WL_CONNECTED) {
c = t;
Serial.println();
Serial.println("Connected!");
digitalWrite(SONOFF_LED, HIGH);
return true;
}
if (buttonActive == true){
digitalWrite(SONOFF, state);
EEPROM.write(0, state);
EEPROM.commit();
buttonActive = false;
}
digitalWrite(SONOFF_LED, HIGH);
delay(125);
digitalWrite(SONOFF_LED, LOW);
delay(375);
Serial.print(WiFi.status());
c++;
}
return false;
}
void loadDataFromWeb() {
if (error.code() != DeserializationError::Ok) {
Serial.println(error.c_str());
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
error = DeserializationError::Ok;
return;
}
//configuration setup
String hostName = jsonContent["device"]["hostname"];
String requestState = jsonContent["state"];
String command = jsonContent["command"];
if (!buttonActive) {
state = (int)jsonContent["value"];
Serial.println("state: " + (String)state);
digitalWrite(SONOFF, state);
EEPROM.write(0, state);
EEPROM.commit();
delay(500);
}
if (command == "reset"){
ESP.reset();
} else if (command == "config") {
CleanEeprom();
EEPROM.commit();
ESP.restart();
}
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
WiFi.hostname(hostName);
}
void sendDataToWeb() {
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
error = deserializeJson(jsonContent, sendHttpRequest());
}
String sendHttpRequest () {
HTTPClient http;
http.setReuse(true);
Serial.println("HTTP url: " + String(host) + String(url) + ""); //Print HTTP return code
http.begin(String(host) + String(url));
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
Serial.println("HTTP request: " + String(requestJson) + ""); //Print HTTP return code
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
if (httpCode == -1) {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return "";
}
return payload;
}
void CleanEeprom() {
for (int i = 1; i < 100; ++i) {
EEPROM.write(i, 0);
}
}
void WriteEeprom (String data, int start = 1) {
for (int i = 0; i < data.length(); ++i)
{
EEPROM.write(start + i, data[i]);
}
EEPROM.commit();
}
String ReadEeprom(int min, int max) {
String localString;
for (int i = min; i < max; ++i) {
localString += char(EEPROM.read(i));
}
return localString;
}
void createWeb()
{
server.on("/", []() {
if (server.args() == 3) {
ssid = server.arg("wifi-ssid");
pasw = server.arg("wifi-pasw");
apiToken = server.arg("apiToken");
if (ssid != "" && pasw != "" && apiToken != "") {
CleanEeprom();
WriteEeprom(ssid);
WriteEeprom(pasw, 33);
WriteEeprom(apiToken, 65);
server.send(200, "application/json", "Restarting esp");
delay(500);
ESP.restart();
}
}
content = "<!DOCTYPE HTML><body>";
content += "<head><style>";
content += "html,body {height: 100%;}";
content += "html {display: table;margin: auto;}";
content += "body {display: table-cell;vertical-align: middle;}";
content += "input {width: 100%;box-sizing: border-box}";
content += "</style></head>";
content += "<h2>WIFI Configuration</h2>";
content += "<h4><b>" + (String)ssidServer + "</b></h4>";
content += "<a href='#'>Refresh</a>";
content += "<div class=\"wifi-list\">";
int n = WiFi.scanNetworks();
if (n == 0)
content += "<label>No networks found...</label>";
else
{
for (int i = 0; i < n; ++i)
{
content += "<a href=\"#\" onclick=\"fillSSID(this.innerHTML)\">" + WiFi.SSID(i) + "</a><br>";
}
}
content += "</div>";
content += "<form method='get' action=''><div class='wifi-form'>";
content += "<label>SSID: </label><input name='wifi-ssid' id='wifi-ssid' length=32 type='text'><br>";
content += "<label>Heslo: </label><input name='wifi-pasw' length=32 type='password'><br>";
content += "<label>Api token: </label><input name='apiToken' length=32 type='password'><br>";
content += "<input type='submit' value='Connect'>";
content += "</div></form>";
content += "<script>";
content += "function fillSSID(value) {\r\n";
content += "document.getElementById(\"wifi-ssid\").value = value;\r\n";
content += "}";
content += "</script>";
content += "</body>";
server.send(200, "text/html", content);
});
}
void setupAP(void) {
WiFi.mode(WIFI_STA);
WiFi.disconnect();
WiFi.softAPdisconnect(true);
delay(100);
int n = WiFi.scanNetworks();
Serial.println("scan done");
if (n == 0)
Serial.println("no networks found");
else
{
Serial.print(n);
Serial.println(" networks found");
for (int i = 0; i < n; ++i)
{
// Print SSID and RSSI for each network found
Serial.print(i + 1);
Serial.print(": ");
Serial.print(WiFi.SSID(i));
Serial.print(" (");
Serial.print(WiFi.RSSI(i));
Serial.print(")");
Serial.println((WiFi.encryptionType(i) == ENC_TYPE_NONE) ? " " : "*");
delay(10);
}
}
delay(100);
WiFi.softAP(ssidServer, paswServer);
Serial.println("softap");
Serial.println("");
Serial.println("WiFi connected");
Serial.print("Local IP: ");
Serial.println(WiFi.localIP());
Serial.print("SoftAP IP: ");
Serial.println(WiFi.softAPIP());
createWeb();
// Start the server
server.begin();
Serial.println("Server started");
Serial.println("over");
}

View File

@@ -0,0 +1,150 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <ArduinoJson.h>
//Variables
const char* ssid = "";
const char* pasw = "";
const char* hwId = "";
const char* server = "http://dev.steelants.cz/vasek/home/api.php";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
int lastState = 0;
//Pins
#define SONOFF 12
#define SONOFF_LED 13
#define SONOFF_BUT 0
void setup() {
Serial.begin(9600);
while (!Serial) continue;
delay(10);
Serial.println('\n');
Serial.println("HW: " + String(hwId));
pinMode(SONOFF, OUTPUT);
pinMode(SONOFF_LED, OUTPUT);
pinMode(SONOFF_BUT, INPUT);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
checkConnection();
Serial.println('\n');
Serial.println("Connection established!");
Serial.print("IP address:");
Serial.println(WiFi.localIP());
Serial.print("MAC address:");
Serial.println(WiFi.macAddress());
}
void loop() {
StaticJsonDocument<250> jsonContent;
jsonContent["token"] = hwId;
if (!digitalRead(SONOFF_BUT)){
jsonContent["values"]["on/off"]["value"] = (int) !lastState;
if (!lastState == 1) {
digitalWrite(SONOFF, HIGH);
} else if (!lastState == 0){
digitalWrite(SONOFF, LOW);
}
while(!digitalRead(SONOFF_BUT)) {
delay(100);
}
}
String requestJson = "";
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
//HTTP CLIENT
HTTPClient http;
http.begin(server);
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
DeserializationError error = deserializeJson(jsonContent, payload);
//configuration setup
String hostName = jsonContent["device"]["hostname"];
String ipAddress = jsonContent["device"]["ipAddress"];
String gateway = jsonContent["device"]["gateway"];
String subnet = jsonContent["device"]["subnet"];
String requestState = jsonContent["state"];
int state = jsonContent["value"];
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
//Set static ip
setStaticIp(ipAddress, gateway, subnet);
WiFi.hostname(hostName);
if(unsuccessfulRounds == 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
if (state != lastState){
if (state == 1 && lastState == 0) {
Serial.println("ON");
digitalWrite(SONOFF, HIGH); // Turn the LED on by making the voltage LOW
} else {
Serial.println("OFF");
digitalWrite(SONOFF, LOW); // Turn the LED on by making the voltage LOW
}
}
lastState = state;
}
bool checkConnection() {
int count = 0;
Serial.print("Waiting for Wi-Fi connection");
while ( count < 30 ) {
if (WiFi.status() == WL_CONNECTED) {
Serial.println();
Serial.println("Connected!");
return (true);
}
digitalWrite(SONOFF, HIGH);
delay(250);
digitalWrite(SONOFF, HIGH);
delay(250);
Serial.print(".");
count++;
}
Serial.println("Timed out.");
return false;
}
void setStaticIp(String ipAddress, String subnet, String gateway){
//Set static ip
IPAddress staticIpAddress;
IPAddress subnetIpAddress;
IPAddress gatewayIpAddress;
if (
staticIpAddress.fromString(ipAddress) &&
subnetIpAddress.fromString(subnet) &&
gatewayIpAddress.fromString(gateway) &&
WiFi.localIP() != staticIpAddress
) {
WiFi.config(staticIpAddress, subnetIpAddress, gatewayIpAddress);
Serial.print("STATIC IP address:");
Serial.println(WiFi.localIP());
}
}

View File

@@ -0,0 +1,221 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266HTTPClient.h>
#include <ArduinoJson.h>
#include <EEPROM.h>
//Variables
const char* ssid = "ssid";
const char* pasw = "pasw";
const char* hwId = "hwId";
const char* server = "http://dev.steelants.cz/vasek/home/api.php";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
StaticJsonDocument<250> jsonContent;
bool buttonActive = false;
int interuptCount = 0;
int realState = 1;
int state = 0;
String requestJson = "";
//Pins
#define SONOFF 12 //12
#define SONOFF_LED 13
#define SONOFF_BUT 0 //0
void ICACHE_RAM_ATTR handleInterrupt ();
void setup() {
Serial.begin(9600);
EEPROM.begin(1);
while (!Serial) continue;
delay(10);
Serial.println('\n');
Serial.println("HW: " + String(hwId));
pinMode(SONOFF_LED, OUTPUT);
pinMode(SONOFF_BUT, INPUT_PULLUP);
pinMode(SONOFF, OUTPUT);
state = EEPROM.read(0);
digitalWrite(SONOFF, state);
realState = state;
attachInterrupt(digitalPinToInterrupt(SONOFF_BUT), handleInterrupt, FALLING);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
checkConnection();
Serial.println('\n');
Serial.println("Connection established!");
Serial.print("IP address:");
Serial.println(WiFi.localIP());
Serial.print("MAC address:");
Serial.println(WiFi.macAddress());
jsonContent = {};
jsonContent["token"] = hwId;
jsonContent["values"]["on/off"]["value"] = (String)realState;
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
}
void loop() {
if(unsuccessfulRounds >= 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
jsonContent = {};
jsonContent["token"] = hwId;
requestJson = "";
if (buttonActive){
jsonContent["values"]["on/off"]["value"] = (String)!realState;
if (!realState == 1) {
digitalWrite(SONOFF, HIGH);
realState = 1;
} else if (!realState == 0){
digitalWrite(SONOFF, LOW);
realState = 0;
}
EEPROM.write(0, 0);
EEPROM.commit();
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
//HTTP CLIENT
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
buttonActive = false;
}
jsonContent = {};
jsonContent["token"] = hwId;
requestJson = "";
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
//HTTP CLIENT
DeserializationError error = deserializeJson(jsonContent, sendHttpRequest(requestJson));
if (error) {
Serial.println(error.c_str());
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return;
}
//configuration setup
String hostName = jsonContent["device"]["hostname"];
String ipAddress = jsonContent["device"]["ipAddress"];
String gateway = jsonContent["device"]["gateway"];
String subnet = jsonContent["device"]["subnet"];
String requestState = jsonContent["state"];
JsonObject object = jsonContent.as<JsonObject>();
if (!object["value"].isNull()) {
state = (int)jsonContent["value"];
}
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
//Set static ip
setStaticIp(ipAddress, gateway, subnet);
WiFi.hostname(hostName);
Serial.println("state: " + (String)state + ", realState: " + (String)realState);
if (state != realState){
if (state == 1 && realState == 0) {
Serial.println("ON state: " + (String)state + ", realState: " + (String)realState);
digitalWrite(SONOFF, HIGH); // Turn the LED on by making the voltage LOW
realState = 1;
} else {
Serial.println("OFF");
digitalWrite(SONOFF, LOW); // Turn the LED on by making the voltage LOW
realState = 0;
}
EEPROM.write(0, realState);
EEPROM.commit();
}
}
void handleInterrupt() {
interuptCount++;
buttonActive = true;
}
String sendHttpRequest (String requestJson) {
HTTPClient http;
http.setReuse(true);
http.begin(server);
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
if (httpCode == -1) {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return "";
}
return payload;
}
bool checkConnection() {
int count = 0;
Serial.print("Waiting for Wi-Fi connection");
while ( count < 30 ) {
if (buttonActive){
if (!realState == 1) {
digitalWrite(SONOFF, HIGH);
realState = 1;
} else if (!realState == 0){
digitalWrite(SONOFF, LOW);
realState = 0;
}
EEPROM.write(0, realState);
EEPROM.commit();
buttonActive = false;
}
digitalWrite(SONOFF_LED, HIGH);
delay(125);
digitalWrite(SONOFF_LED, LOW);
delay(125);
if (WiFi.status() == WL_CONNECTED) {
Serial.println();
Serial.println("Connected!");
digitalWrite(SONOFF_LED, LOW);
return (true);
}
Serial.print(".");
count++;
}
Serial.println("Timed out.");
return false;
}
void setStaticIp(String ipAddress, String subnet, String gateway){
//Set static ip
IPAddress staticIpAddress;
IPAddress subnetIpAddress;
IPAddress gatewayIpAddress;
if (
staticIpAddress.fromString(ipAddress) &&
subnetIpAddress.fromString(subnet) &&
gatewayIpAddress.fromString(gateway) &&
WiFi.localIP() != staticIpAddress
) {
WiFi.config(staticIpAddress, subnetIpAddress, gatewayIpAddress);
Serial.print("STATIC IP address:");
Serial.println(WiFi.localIP());
}
}

View File

@@ -0,0 +1,375 @@
//Includes
#include <ESP8266WiFi.h>
#include <ESP8266WebServer.h>
#include <WiFiClientSecure.h>
#include <ESP8266HTTPClient.h>
#define ARDUINOJSON_DECODE_UNICODE 1
#include <ArduinoJson.h>
#include <EEPROM.h>
#include "ESP8266httpUpdate.h"
//Variables
const char* ssidServer = "";
const char* paswServer = "";
String ssid = "";
String pasw = "";
String apiToken = "";
const int httpsPort = 443;
const char* host = "http://dev.steelants.cz";
const char* url = "/vasek/home/api.php";
const char* fingerprint = "";
const char* host2 = "dev.steelants.cz";
const char* url2 = "/vasek/home/update.php";
String content;
bool conf = false;
bool buttonActive = false;
int state = 0;
String requestJson = "";
int unsuccessfulRounds = 0; //Unsucesful atmpt counter
ESP8266WebServer server(80);
StaticJsonDocument<250> jsonContent;
DeserializationError error;
//Pins
#define SONOFF 12
#define SONOFF_LED 13
#define SONOFF_BUT 0 //0
void ICACHE_RAM_ATTR handleInterrupt ();
void setup() {
Serial.begin(9600);
EEPROM.begin(100);
while (!Serial) continue;
delay(10);
//read saved data
ssid = ReadEeprom(1, 33);
pasw = ReadEeprom(33, 65);
apiToken = ReadEeprom(65, 97);
//set pins
pinMode(SONOFF_LED, OUTPUT);
pinMode(SONOFF_BUT, INPUT_PULLUP);
pinMode(SONOFF, OUTPUT);
state = EEPROM.read(0);
digitalWrite(SONOFF, state);
attachInterrupt(digitalPinToInterrupt(SONOFF_BUT), handleInterrupt, FALLING);
//wifi
if (ssid != "") {
WiFi.disconnect();
WiFi.softAPdisconnect(true);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, pasw);
conf = wifiVerify(20);
if (conf) {
configTime(3 * 3600, 0, "pool.ntp.org");
WiFiClientSecure client;
Serial.print("connecting to ");
Serial.println(host2);
client.setInsecure();
if (!client.connect(host2, httpsPort)) {
Serial.println("connection failed");
return;
}
if (client.verify(fingerprint, host2)) {
Serial.println("certificate matches");
} else {
Serial.println("certificate doesn't match");
return;
}
Serial.print("Starting OTA from: ");
Serial.println(url2
);
auto ret = ESPhttpUpdate.update(client, host2, 80, url2);
delay(500);
switch(ret) {
case HTTP_UPDATE_FAILED:
Serial.printf("HTTP_UPDATE_FAILD Error (%d): %s", ESPhttpUpdate.getLastError(), ESPhttpUpdate.getLastErrorString().c_str());
Serial.println();
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_NO_UPDATES:
Serial.println("HTTP_UPDATE_NO_UPDATES");
Serial.println();
Serial.println();
break;
case HTTP_UPDATE_OK:
Serial.println("HTTP_UPDATE_OK");
Serial.println();
Serial.println();
Serial.println();
break;
}
delay(500);
jsonContent = {};
jsonContent["token"] = apiToken;
jsonContent["values"]["on/off"]["value"] = (String)state;
jsonContent["settings"]["network"]["ip"] = WiFi.localIP().toString();
jsonContent["settings"]["network"]["mac"] = WiFi.macAddress();
jsonContent["settings"]["firmware_hash"] = ESP.getSketchMD5();
sendDataToWeb();
return;
}
}
setupAP();
}
void loop() {
if (conf) {
if (unsuccessfulRounds >= 5) {
Serial.println("RESTARTING ESP");
ESP.restart();
}
jsonContent = {};
jsonContent["token"] = apiToken;
requestJson = "";
if (buttonActive) {
jsonContent["values"]["on/off"]["value"] = (String)state;
digitalWrite(SONOFF, state);
EEPROM.write(0, state);
EEPROM.commit();
sendDataToWeb();
buttonActive = false;
delay(500);
} else {
sendDataToWeb();
loadDataFromWeb();
}
} else {
server.handleClient();
}
}
void handleInterrupt() {
buttonActive = true;
state = !state;
digitalWrite(SONOFF, state);
}
bool wifiVerify(int t) {
int c = 0;
Serial.println("Waiting for Wifi to connect to Shelly1");
while (c < t) {
if (WiFi.status() == WL_CONNECTED) {
c = t;
Serial.println();
Serial.println("Connected!");
digitalWrite(SONOFF_LED, HIGH);
return true;
}
if (buttonActive == true){
digitalWrite(SONOFF, state);
EEPROM.write(0, state);
EEPROM.commit();
buttonActive = false;
}
digitalWrite(SONOFF_LED, HIGH);
delay(125);
digitalWrite(SONOFF_LED, LOW);
delay(375);
Serial.print(WiFi.status());
c++;
}
return false;
}
void loadDataFromWeb() {
if (error.code() != DeserializationError::Ok) {
Serial.println(error.c_str());
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
error = DeserializationError::Ok;
return;
}
//configuration setup
String hostName = jsonContent["device"]["hostname"];
String requestState = jsonContent["state"];
String command = jsonContent["command"];
if (!buttonActive) {
state = (int)jsonContent["value"];
Serial.println("state: " + (String)state);
digitalWrite(SONOFF, state);
EEPROM.write(0, state);
EEPROM.commit();
delay(500);
}
if (command == "reset"){
ESP.reset();
} else if (command == "config") {
CleanEeprom();
EEPROM.commit();
ESP.restart();
}
if (requestState != "succes") {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
} else if (requestState == "succes") {
unsuccessfulRounds = 0;
}
WiFi.hostname(hostName);
}
void sendDataToWeb() {
serializeJson(jsonContent, requestJson);
Serial.println("JSON: " + requestJson);
error = deserializeJson(jsonContent, sendHttpRequest());
}
String sendHttpRequest () {
HTTPClient http;
http.setReuse(true);
Serial.println("HTTP url: " + String(host) + String(url) + ""); //Print HTTP return code
http.begin(String(host) + String(url));
http.addHeader("Content-Type", "text/plain"); //Specify content-type header
Serial.println("HTTP request: " + String(requestJson) + ""); //Print HTTP return code
int httpCode = http.POST(requestJson);
String payload = http.getString(); //Get the response payload
http.end();
Serial.println("HTTP CODE: " + String(httpCode) + ""); //Print HTTP return code
Serial.println("HTTP BODY: " + String(payload) + ""); //Print request response payload
if (httpCode == -1) {
unsuccessfulRounds++;
Serial.println("UNSUCCESSFUL ROUND NUMBER " + String(unsuccessfulRounds) + "FROM 5");
return "";
}
return payload;
}
void CleanEeprom() {
for (int i = 1; i < 100; ++i) {
EEPROM.write(i, 0);
}
}
void WriteEeprom (String data, int start = 1) {
for (int i = 0; i < data.length(); ++i)
{
EEPROM.write(start + i, data[i]);
}
EEPROM.commit();
}
String ReadEeprom(int min, int max) {
String localString;
for (int i = min; i < max; ++i) {
localString += char(EEPROM.read(i));
}
return localString;
}
void createWeb()
{
server.on("/", []() {
if (server.args() == 3) {
ssid = server.arg("wifi-ssid");
pasw = server.arg("wifi-pasw");
apiToken = server.arg("apiToken");
if (ssid != "" && pasw != "" && apiToken != "") {
CleanEeprom();
WriteEeprom(ssid);
WriteEeprom(pasw, 33);
WriteEeprom(apiToken, 65);
server.send(200, "application/json", "Restarting esp");
delay(500);
ESP.restart();
}
}
content = "<!DOCTYPE HTML><body>";
content += "<head><style>";
content += "html,body {height: 100%;}";
content += "html {display: table;margin: auto;}";
content += "body {display: table-cell;vertical-align: middle;}";
content += "input {width: 100%;box-sizing: border-box}";
content += "</style></head>";
content += "<h2>WIFI Configuration</h2>";
content += "<h4><b>" + (String)ssidServer + "</b></h4>";
content += "<a href='#'>Refresh</a>";
content += "<div class=\"wifi-list\">";
int n = WiFi.scanNetworks();
if (n == 0)
content += "<label>No networks found...</label>";
else
{
for (int i = 0; i < n; ++i)
{
content += "<a href=\"#\" onclick=\"fillSSID(this.innerHTML)\">" + WiFi.SSID(i) + "</a><br>";
}
}
content += "</div>";
content += "<form method='get' action=''><div class='wifi-form'>";
content += "<label>SSID: </label><input name='wifi-ssid' id='wifi-ssid' length=32 type='text'><br>";
content += "<label>Heslo: </label><input name='wifi-pasw' length=32 type='password'><br>";
content += "<label>Api token: </label><input name='apiToken' length=32 type='password'><br>";
content += "<input type='submit' value='Connect'>";
content += "</div></form>";
content += "<script>";
content += "function fillSSID(value) {\r\n";
content += "document.getElementById(\"wifi-ssid\").value = value;\r\n";
content += "}";
content += "</script>";
content += "</body>";
server.send(200, "text/html", content);
});
}
void setupAP(void) {
WiFi.mode(WIFI_STA);
WiFi.disconnect();
WiFi.softAPdisconnect(true);
delay(100);
int n = WiFi.scanNetworks();
Serial.println("scan done");
if (n == 0)
Serial.println("no networks found");
else
{
Serial.print(n);
Serial.println(" networks found");
for (int i = 0; i < n; ++i)
{
// Print SSID and RSSI for each network found
Serial.print(i + 1);
Serial.print(": ");
Serial.print(WiFi.SSID(i));
Serial.print(" (");
Serial.print(WiFi.RSSI(i));
Serial.print(")");
Serial.println((WiFi.encryptionType(i) == ENC_TYPE_NONE) ? " " : "*");
delay(10);
}
}
delay(100);
WiFi.softAP(ssidServer, paswServer);
Serial.println("softap");
Serial.println("");
Serial.println("WiFi connected");
Serial.print("Local IP: ");
Serial.println(WiFi.localIP());
Serial.print("SoftAP IP: ");
Serial.println(WiFi.softAPIP());
createWeb();
// Start the server
server.begin();
Serial.println("Server started");
Serial.println("over");
}

View File

@@ -0,0 +1,71 @@
<!DOCTYPE html>
<body>
<head>
<style>
html,
body {
height: 100%;
}
html {
display: table;
margin: auto;
font-family: "Metropolis", sans-serif;
}
body {
display: table-cell;
vertical-align: middle;
background: #182239;
color: #d4def7;
}
input {
width: 100%;
box-sizing: border-box;
line-height: 1.5;
background: #121a2b;
border-radius: 3px;
border: 0px solid transparent;
color: #d4def7;
padding: 0.5em 0.8em;
height: 2.5rem;
line-height: 1.5;
background: #121a2b;
width: 100%;
display: block;
}
a{
display: block;
color: #DDE7F5;
text-decoration:underline;
}
</style>
</head>
<h2>WIFI Configuration</h2>
<a href="#">Refresh</a>
<form>
<div class="wifi-list">
<a href="#" onclick="fillSSID(this.innerHTML)">WifiName</a><br>
<a href="#" onclick="fillSSID(this.innerHTML)">WifiName</a><br>
<a href="#" onclick="fillSSID(this.innerHTML)">WifiName</a><br>
<a href="#" onclick="fillSSID(this.innerHTML)">WifiName</a><br>
<a href="#" onclick="fillSSID(this.innerHTML)">WifiName</a><br>
<a href="#" onclick="fillSSID(this.innerHTML)">WifiName</a><br>
</div>
<div class="wifi-form">
<input id="wifi-ssid" type="text"><br>
<input id="password" type="text"><br>
<input type="submit" value="Connect">
</div>
</form>
<script>
function fillSSID(value) {
document.getElementById("wifi-ssid").value = value;
}
</script>
</body>

View File

@@ -0,0 +1,3 @@
{
"folders": []
}

175
api.php
View File

@@ -31,6 +31,7 @@ if (!$restAcess){
//Log //Log
$logManager = new LogManager(); $logManager = new LogManager();
$apiLogManager = new LogManager('./app/logs/api/'. date("Y-m-d").'.log');
//DB Conector //DB Conector
Db::connect (DBHOST, DBUSER, DBPASS, DBNAME); Db::connect (DBHOST, DBUSER, DBPASS, DBNAME);
@@ -39,17 +40,25 @@ Db::connect (DBHOST, DBUSER, DBPASS, DBNAME);
$json = file_get_contents('php://input'); $json = file_get_contents('php://input');
$obj = json_decode($json, true); $obj = json_decode($json, true);
//Log RAW api request
if (API_DEBUGMOD == 1) {
$apiLogManager->write("[API] request body\n" . json_encode($obj, JSON_PRETTY_PRINT), LogRecordType::INFO);
}
//zabespecit proti Ddosu //zabespecit proti Ddosu
if (isset($obj['user']) && $obj['user'] != ''){ if (isset($obj['user']) && $obj['user'] != ''){
//user at home //user at home
$user = UserManager::getUser($obj['user']); $user = UserManager::getUser($obj['user']);
$userAtHome = $user['at_home'];
if (!empty($user)) { if (!empty($user)) {
$userId = $user['user_id']; $userId = $user['user_id'];
$atHome = $obj['atHome']; $atHome = $obj['atHome'];
UserManager::atHome($userId, $atHome); if($userAtHome != $atHome){
$logManager->write("[Record] user " . $userId . "changet his home state to " . $atHome . RECORDTIMOUT , LogRecordType::WARNING); UserManager::atHome($userId, $atHome);
$logManager->write("[USER] user " . $userId . " changet his home state to " . $atHome , LogRecordType::INFO);
}
echo 'Saved: ' . $atHome; echo 'Saved: ' . $atHome;
header("HTTP/1.1 200 OK"); header($_SERVER["SERVER_PROTOCOL"]." 200 OK");
die(); die();
} }
} }
@@ -60,8 +69,8 @@ if (DEBUGMOD != 1) {
echo json_encode(array( echo json_encode(array(
'state' => 'unsuccess', 'state' => 'unsuccess',
'errorMSG' => "Using API from your IP insnt alowed!", 'errorMSG' => "Using API from your IP insnt alowed!",
)); ), JSON_PRETTY_PRINT);
header("HTTP/1.1 401 Unauthorized"); header($_SERVER["SERVER_PROTOCOL"]." 401 Unauthorized");
$logManager->write("[API] acces denied from " . $_SERVER['REMOTE_ADDR'], LogRecordType::WARNING); $logManager->write("[API] acces denied from " . $_SERVER['REMOTE_ADDR'], LogRecordType::WARNING);
exit(); exit();
} }
@@ -70,6 +79,9 @@ if (DEBUGMOD != 1) {
//automationExecution //automationExecution
try { try {
AutomationManager::executeAll(); AutomationManager::executeAll();
$fallbackManager = new FallbackManager(RANGES);
$fallbackManager->check();
//LogKeeper::purge(LOGTIMOUT);
} catch (\Exception $e) { } catch (\Exception $e) {
$logManager->write("[Automation] Something happen during automation execution", LogRecordType::ERROR); $logManager->write("[Automation] Something happen during automation execution", LogRecordType::ERROR);
} }
@@ -79,67 +91,136 @@ try {
RecordManager::clean(RECORDTIMOUT); RecordManager::clean(RECORDTIMOUT);
} catch (\Exception $e) { } catch (\Exception $e) {
$logManager->write("[Record] cleaning record older that " . RECORDTIMOUT , LogRecordType::ERROR); $logManager->write("[Record] cleaning record older that " . RECORDTIMOUT , LogRecordType::ERROR);
} }
//Variables //Variables
$token = $obj['token']; $token = $obj['token'];
$values = null; $values = null;
$settings = null;
$deviceLogs = null;
$command = "null";
if (isset($obj['values'])) { if (isset($obj['values'])) {
$values = $obj['values']; $values = $obj['values'];
} }
if (isset($obj['settings'])) {
$settings = $obj['settings'];
}
if (isset($obj['logs'])) {
$deviceLogs = $obj['logs'];
}
//Checks //Checks
if ($token == null || $token == "") { if ($token == null || $token == "") {
echo json_encode(array( echo json_encode(array(
'state' => 'unsuccess', 'state' => 'unsuccess',
'errorMSG' => "Missing Value Token in JSON payload", 'errorMSG' => "Missing Value Token in JSON payload",
)); ), JSON_PRETTY_PRINT);
header("HTTP/1.1 401 Unauthorized"); header($_SERVER["SERVER_PROTOCOL"]." 401 Unauthorized");
die(); die();
} }
//Vstupní Checky //Vstupní Checky
if (!DeviceManager::registeret($token)) { if (!DeviceManager::registeret($token)) {
$notificationMng = new NotificationManager;
$notificationData = [];
$notificationData = [ $notificationData = [
'title' => 'Info', 'title' => 'Info',
'body' => 'New device Detected', 'body' => 'New device Detected Found',
'icon' => '', 'icon' => BASEDIR . '/app/templates/images/icon-192x192.png',
]; ];
$deviceId = DeviceManager::create($token, $token); $deviceId = DeviceManager::create($token, $token);
foreach ($values as $key => $value) { foreach ($values as $key => $value) {
if (!SubDeviceManager::getSubDeviceByMaster($deviceId, $key)) { if (!SubDeviceManager::getSubDeviceByMaster($deviceId, $key)) {
SubDeviceManager::create($deviceId, $key, UNITS[$key]); SubDeviceManager::create($deviceId, $key, UNITS[$key]);
} }
if ($notificationData != []) {
$subscribers = $notificationMng::getSubscription();
foreach ($subscribers as $key => $subscriber) {
$logManager->write("[NOTIFICATION] SENDING TO" . $subscriber['id'] . " ", LogRecordType::INFO);
$notificationMng::sendSimpleNotification(SERVERKEY, $subscriber['token'], $notificationData);
}
}
} }
//Notification for newly added Device //Notification for newly added Device
$subscribers = $notificationMng::getSubscription(); $subscribers = $notificationMng::getSubscription();
foreach ($subscribers as $key => $subscriber) { foreach ($subscribers as $key => $subscriber) {
$logManager->write("[NOTIFICATION] SENDING TO" . $subscriber['id'] . " "); $logManager->write("[NOTIFICATION] SENDING TO" . $subscriber['id'] . " ", LogRecordType::INFO);
$notificationMng::sendSimpleNotification(SERVERKEY, $subscriber['token'], $notificationData); $notificationMng::sendSimpleNotification(SERVERKEY, $subscriber['token'], $notificationData);
} }
header("HTTP/1.1 401 Unauthorized"); header($_SERVER["SERVER_PROTOCOL"]." 401 Unauthorized");
echo json_encode(array( echo json_encode(array(
'state' => 'unsuccess', 'state' => 'unsuccess',
'errorMSG' => "Device not registeret", 'errorMSG' => "Device not registeret",
)); ), JSON_PRETTY_PRINT);
$logManager->write("[API] Registering Device", LogRecordType::INFO); $logManager->write("[API] Registering Device", LogRecordType::INFO);
exit(); exit();
} }
if (!DeviceManager::approved($token)) { if (!DeviceManager::approved($token)) {
header("HTTP/1.1 401 Unauthorized"); header($_SERVER["SERVER_PROTOCOL"]." 401 Unauthorized");
echo json_encode(array( echo json_encode(array(
'state' => 'unsuccess', 'state' => 'unsuccess',
'errorMSG' => "Unaproved Device", 'errorMSG' => "Unaproved Device",
)); ), JSON_PRETTY_PRINT);
exit(); exit();
} }
// Diagnostic Data Write to DB
if ($settings != null && $settings != ""){
$data = ['mac' => $settings["network"]["mac"], 'ip_address' => $settings["network"]["ip"]];
if (array_key_exists("firmware_hash", $settings)) {
$data['firmware_hash'] = $settings["firmware_hash"];
}
DeviceManager::editByToken($token, $data);
$jsonAnswer = [
'state' => 'succes',
'command' => $command,
];
echo json_encode($jsonAnswer, JSON_PRETTY_PRINT);
header($_SERVER["SERVER_PROTOCOL"]." 200 OK");
die();
}
// Issuing command
if ($command == "null"){
$device = DeviceManager::getDeviceByToken($token);
$deviceId = $device['device_id'];
$deviceCommand = $device["command"];
if ($deviceCommand != '' && $deviceCommand != null && $deviceCommand != "null")
{
$command = $deviceCommand;
$data = [
'command'=>'null'
];
DeviceManager::editByToken($token, $data);
$logManager->write("[API] Device_ID " . $deviceId . " executing command " . $command, LogRecordType::INFO);
}
}
// Diagnostic Logs Write To log File
if ($deviceLogs != null && $deviceLogs != ""){
foreach ($deviceLogs as $log) {
$logManager->write("[Device Log Msg] Device_ID " . $deviceId . "->" . $log, LogRecordType::ERROR);
}
$jsonAnswer = [
'state' => 'succes',
'command' => $command,
];
echo json_encode($jsonAnswer, JSON_PRETTY_PRINT);
header($_SERVER["SERVER_PROTOCOL"]." 200 OK");
die();
}
// Subdevices first data! // Subdevices first data!
if ($values != null || $values != "") { if ($values != null && $values != "") {
//ZAPIS //ZAPIS
$device = DeviceManager::getDeviceByToken($token); $device = DeviceManager::getDeviceByToken($token);
@@ -148,7 +229,7 @@ if ($values != null || $values != "") {
if (!SubDeviceManager::getSubDeviceByMaster($deviceId, $key)) { if (!SubDeviceManager::getSubDeviceByMaster($deviceId, $key)) {
SubDeviceManager::create($deviceId, $key, UNITS[$key]); SubDeviceManager::create($deviceId, $key, UNITS[$key]);
} }
RecordManager::create($deviceId, $key, round($value['value'],2)); RecordManager::create($deviceId, $key, round($value['value'],3));
$logManager->write("[API] Device_ID " . $deviceId . " writed value " . $key . ' ' . $value['value'], LogRecordType::INFO); $logManager->write("[API] Device_ID " . $deviceId . " writed value " . $key . ' ' . $value['value'], LogRecordType::INFO);
//notification //notification
@@ -158,25 +239,26 @@ if ($values != null || $values != "") {
switch ($key) { switch ($key) {
case 'door': case 'door':
$notificationData = [ $notificationData = [
'title' => 'Info', 'title' => 'Info',
'body' => 'Someone just open up '.$device['name'], 'body' => 'Someone just open up '.$device['name'],
'icon' => '', 'icon' => BASEDIR . '/app/templates/images/icon-192x192.png',
]; ];
break; break;
case 'water': case 'water':
$notificationData = [ $notificationData = [
'title' => 'Alert', 'title' => 'Alert',
'body' => 'Wather leak detected by '.$device['name'], 'body' => 'Wather leak detected by '.$device['name'],
'icon' => '', 'icon' => BASEDIR . '/app/templates/images/icon-192x192.png',
]; ];
break; break;
} }
if (DEBUGMOD) $notificationData['body'] .= ' value='.$value['value']; if (DEBUGMOD) $notificationData['body'] .= ' value='.$value['value'];
if ($notificationData != []) { if ($notificationData != []) {
$subscribers = $notificationMng::getSubscription(); $subscribers = $notificationMng::getSubscription();
foreach ($subscribers as $key => $subscriber) { foreach ($subscribers as $key => $subscriber) {
$logManager->write("[NOTIFICATION] SENDING TO" . $subscriber['id'] . " "); $logManager->write("[NOTIFICATION] SENDING TO" . $subscriber['id'] . " ", LogRecordType::INFO);
$notificationMng::sendSimpleNotification(SERVERKEY, $subscriber['token'], $notificationData); $notificationMng::sendSimpleNotification(SERVERKEY, $subscriber['token'], $notificationData);
} }
} }
@@ -185,22 +267,26 @@ if ($values != null || $values != "") {
$hostname = strtolower($device['name']); $hostname = strtolower($device['name']);
$hostname = str_replace(' ', '_', $hostname); $hostname = str_replace(' ', '_', $hostname);
//upravit format na setings-> netvork etc
$jsonAnswer = [ $jsonAnswer = [
'device' => [ 'device' => [
'hostname' => $hostname, 'hostname' => $hostname,
'ipAddress' => $device['ip_address'],
'subnet' => $device['subnet'],
'gateway' => $device['gateway'],
], ],
'state' => 'succes', 'state' => 'succes',
'command' => $command,
]; ];
$subDevicesTypeList = SubDeviceManager::getSubDeviceSTypeForMater($deviceId); $subDevicesTypeList = SubDeviceManager::getSubDeviceSTypeForMater($deviceId);
if (!in_array($subDevicesTypeList, ['on/off', 'door', 'water'])) { if (!in_array($subDevicesTypeList, ['on/off', 'door', 'water'])) {
$jsonAnswer['sleepTime'] = $device['sleep_time']; $jsonAnswer['device']['sleepTime'] = $device['sleep_time'];
} }
echo json_encode($jsonAnswer); echo json_encode($jsonAnswer, JSON_PRETTY_PRINT);
header("HTTP/1.1 200 OK"); header($_SERVER["SERVER_PROTOCOL"]." 200 OK");
} else { } else {
//Vypis //Vypis
//TODO: doděla uložení výpisu jinými slovy zda li byl comman vykonán
$device = DeviceManager::getDeviceByToken($token); $device = DeviceManager::getDeviceByToken($token);
$deviceId = $device['device_id']; $deviceId = $device['device_id'];
@@ -214,21 +300,24 @@ if ($values != null || $values != "") {
$subDeviceLastReordValue = $subDeviceLastReord['value']; $subDeviceLastReordValue = $subDeviceLastReord['value'];
if ($subDeviceLastReord['execuded'] == 0){ if ($subDeviceLastReord['execuded'] == 0){
$logManager->write("[API] subDevice id ".$subDeviceId . " executed comand with value " .$subDeviceLastReordValue . " record id " . $subDeviceLastReord['record_id'] . " executed " . $subDeviceLastReord['execuded']); $logManager->write("[API] subDevice_ID ".$subDeviceId . " executed comand with value " .$subDeviceLastReordValue . " record id " . $subDeviceLastReord['record_id'] . " executed " . $subDeviceLastReord['execuded'], LogRecordType::INFO);
RecordManager::setExecuted($subDeviceLastReord['record_id']); RecordManager::setExecuted($subDeviceLastReord['record_id']);
} }
echo json_encode(array( echo json_encode(array(
'device' => [ 'device' => [
'hostname' => $device['name'], 'hostname' => $device['name'],
'sleepTime' => $device['sleep_time'], 'ipAddress' => $device['ip_address'],
], 'subnet' => $device['subnet'],
'state' => 'succes', 'gateway' => $device['gateway'],
'value' => $subDeviceLastReordValue ],
)); 'state' => 'succes',
header("HTTP/1.1 200 OK"); 'value' => $subDeviceLastReordValue,
} 'command' => $command,
), JSON_PRETTY_PRINT);
header($_SERVER["SERVER_PROTOCOL"]." 200 OK");
}
unset($logManager); unset($logManager);
Db::disconect(); Db::disconect();
die(); die();

43
apiFront.php Normal file
View File

@@ -0,0 +1,43 @@
<?php
/** Includes **/
include_once('./config.php');
//Autoloader
$files = scandir('./app/class/');
$files = array_diff($files, array(
'.',
'..',
'app',
'ChartJS.php',
'ChartJS_Line.php',
'ChartManager.php',
'DashboardManager.php',
'Partial.php',
'Form.php',
'Route.php',
'Template.php',
'Ajax.php',
));
foreach($files as $file) {
include './app/class/'. $file;
}
//Log
$apiLogManager = new LogManager('./app/logs/apiFront/'. date("Y-m-d").'.log');
//DB Conector
Db::connect (DBHOST, DBUSER, DBPASS, DBNAME);
//Read API data
$json = file_get_contents('php://input');
$obj = json_decode($json, true);
//Log RAW api request
if (API_DEBUGMOD == 1) {
$apiLogManager->write("[API] request body\n" . json_encode($obj, JSON_PRETTY_PRINT), LogRecordType::INFO);
}
unset($logManager);
Db::disconect();
die();

View File

@@ -18,8 +18,10 @@ class AutomationManager{
} }
public function create ($name, $onDays, $doCode, $ifCode, $automationId = "") { public function create ($name, $onDays, $doCode, $ifCode, $automationId = "") {
$userId = UserManager::getUserData('user_id');
$scene = array ( $scene = array (
'name' => $name, 'name' => $name,
'owner_id' => $userId,
'on_days' => $onDays, 'on_days' => $onDays,
'if_something' => $ifCode, 'if_something' => $ifCode,
'do_something' => $doCode, 'do_something' => $doCode,
@@ -77,9 +79,21 @@ class AutomationManager{
} }
} else if ($onValue['type'] == 'outHome') { } else if ($onValue['type'] == 'outHome') {
//TODO: Add Ovner to automation
$userHomeStatus = UserManager::getUserData('at_home', $onValue['value']);
if ($userHomeStatus == 'false' && $automation['executed'] == 0) {
$run = true;
} else if ($userHomeStatus == 'true' && $automation['executed'] == 1) {
$restart = true;
}
} else if ($onValue['type'] == 'inHome') { } else if ($onValue['type'] == 'inHome') {
//TODO: Add Ovner to automation
$userHomeStatus = UserManager::getUserData('at_home', $onValue['value']);
if ($userHomeStatus == 'true' && $automation['executed'] == 0) {
$run = true;
} else if ($userHomeStatus == 'false' && $automation['executed'] == 1) {
$restart = true;
}
} else if ($onValue['type'] == 'noOneHome') { } else if ($onValue['type'] == 'noOneHome') {
$users = UserManager::getUsers(); $users = UserManager::getUsers();
$membersHome = 0; $membersHome = 0;
@@ -106,6 +120,18 @@ class AutomationManager{
} else if ($membersHome > 0 && $automation['executed'] == 0){ } else if ($membersHome > 0 && $automation['executed'] == 0){
$run = true; $run = true;
} }
} else if ($onValue['type'] == 'atDeviceValue') {
$subDeviceId = SubDeviceManager::getSubDeviceByMaster($onValue['value']['deviceID'], $onValue['value']['type'])["subdevice_id"];
$lastValue = RecordManager::getLastRecord($subDeviceId);
if ($lastValue['value'] == $onValue['value']['value'] && $automation['executed'] == 0) {
$run = true;
} else if ($lastValue['value'] != $onValue['value']['value'] && $automation['executed'] == 1){
$restart = true;
}
} }
//finalization //finalization
@@ -120,18 +146,23 @@ class AutomationManager{
$subscribers = NotificationManager::getSubscription(); $subscribers = NotificationManager::getSubscription();
$i = 0; $i = 0;
foreach ($subscribers as $key => $subscriber) { $notificationMng = new NotificationManager;
$logManager->write("[NOTIFICATION] SENDING NOTIFICATION TO" . $subscriber['id'] . " was executed" . $i); $notificationData = [
$title = 'Automatization '.$automation['name']." was just executed"; 'title' => 'Automatization',
$notification = new Notification(SERVERKEY); 'body' => 'Automatization '.$automation['name']." was just executed",
$notification->to($subscriber['token']); 'icon' => BASEDIR . '/app/templates/images/icon-192x192.png',
$notification->notification($title, '' , '', ''); ];
$notification->send();
$notification = null; if ($notificationData != []) {
$subscribers = $notificationMng::getSubscription();
foreach ($subscribers as $key => $subscriber) {
$logManager->write("[NOTIFICATION/AUTOOMATION] SENDING TO" . $subscriber['id'] . " ");
$notificationMng::sendSimpleNotification(SERVERKEY, $subscriber['token'], $notificationData);
}
} }
$logManager->write("[AUTOMATIONS] automation id ". $automation['automation_id'] . " was executed"); $logManager->write("[AUTOMATIONS] automation id ". $automation['automation_id'] . " was executed");
Db::edit('automation', array('executed' => 1), 'WHERE automation_id = ?', array($automation['automation_id'])); Db::edit('automation', array('executed' => 1, 'execution_time' => date("Y-m-d H:i:s")), 'WHERE automation_id = ?', array($automation['automation_id']));
} else if ($restart) { } else if ($restart) {
$logManager->write("[AUTOMATIONS] automation id ". $automation['automation_id'] . " was restarted"); $logManager->write("[AUTOMATIONS] automation id ". $automation['automation_id'] . " was restarted");
Db::edit('automation', array('executed' => 0), 'WHERE automation_id = ?', array($automation['automation_id'])); Db::edit('automation', array('executed' => 0), 'WHERE automation_id = ?', array($automation['automation_id']));

View File

@@ -18,14 +18,20 @@ class DeviceManager{
return Db::loadOne("SELECT * FROM devices WHERE token = ?", array($deviceToken)); return Db::loadOne("SELECT * FROM devices WHERE token = ?", array($deviceToken));
} }
function getDeviceByMac($deviceMac) {
return Db::loadOne("SELECT * FROM devices WHERE mac = ?", array($deviceMac));
}
function getDeviceById($deviceId) { function getDeviceById($deviceId) {
return Db::loadOne("SELECT * FROM devices WHERE device_id = ?", array($deviceId)); return Db::loadOne("SELECT * FROM devices WHERE device_id = ?", array($deviceId));
} }
public function create ($name, $token) { public function create ($name, $token) {
$defaultRoom = RoomManager::getDefaultRoomId();
$device = array ( $device = array (
'name' => $name, 'name' => $name,
'token' => $token, 'token' => $token,
'room_id' => $defaultRoom,
); );
try { try {
Db::add ('devices', $device); Db::add ('devices', $device);
@@ -45,6 +51,15 @@ class DeviceManager{
} }
} }
public function editByToken ($token, $values = []) {
try {
Db::edit ('devices', $values, 'WHERE token = ?', array($token));
} catch(PDOException $error) {
echo $error->getMessage();
die();
}
}
/** /**
* [assignRoom Přiřazení zařízení do třídy] * [assignRoom Přiřazení zařízení do třídy]
* @param [type] $roomId [číslo místnosti do kter se má zařízení přiřadit] * @param [type] $roomId [číslo místnosti do kter se má zařízení přiřadit]

View File

@@ -0,0 +1,44 @@
<?php
/**
*
*/
class FallbackManager
{
public $deviceDefinitions = "";
function __construct($deviceDefinition)
{
$this->deviceDefinitions = $deviceDefinition;
}
function check(){
//TODO: FIX IT
$allDevicesData = DeviceManager::getAllDevices();
foreach ($allDevicesData as $deviceKey => $deviceValue) {
$allSubDevicesData = SubDeviceManager::getAllSubDevices($deviceValue['device_id']);
foreach ($allSubDevicesData as $subDeviceKey => $subDeviceValue) {
if (!isset($this->deviceDefinitions[$subDeviceValue['type']]["fallBack"])) {
continue;
}
if (!isset($this->deviceDefinitions[$subDeviceValue['type']]["fallBackTime"])) {
continue;
}
$lastRecord = RecordManager::getLastRecord($subDeviceValue['subdevice_id']);
if ($lastRecord["value"] == $this->deviceDefinitions[$subDeviceValue['type']]["fallBack"]) {
continue;
}
$minutes = (time() - strtotime($lastRecord['time'])) / 60;
if ( $minutes > $this->deviceDefinitions[$subDeviceValue['type']]["fallBackTime"]){
RecordManager::create($deviceValue['device_id'], $subDeviceValue['type'], $this->deviceDefinitions[$subDeviceValue['type']]["fallBack"]);
}
}
}
}
}

View File

@@ -9,6 +9,25 @@ class LogRecordType{
const INFO = 'info'; const INFO = 'info';
} }
class LogKeeper
{
function purge($days){
$todayFileName = date("Y-m-d").'.log';
$seconds = $days * 86400;
$logFiles = scandir('./app/logs/');
foreach ($logFiles as $key => $file) {
if (in_array($file,array(".","..", ".gitkeep", $todayFileName)))
{
continue;
}
if (filemtime($file) > $seconds) {
unlink('./app/logs/'.$file);
}
}
}
}
class LogManager class LogManager
{ {
@@ -27,7 +46,9 @@ class LogManager
function write($value, $type = LogRecordType::ERROR){ function write($value, $type = LogRecordType::ERROR){
$record = "[".date("H:m:s")."][".$type."]" . $value . "\n"; $record = "[".date("H:m:s")."][".$type."]" . $value . "\n";
$record = Utilities::stringInsert($record,"\n",65); if (strlen($record) > 65 ) {
$record = Utilities::stringInsert($record,"\n",65);
}
fwrite($this->logFile, $record); fwrite($this->logFile, $record);
} }

View File

@@ -0,0 +1,18 @@
<?php
/**
*
*/
class NetvorkManager
{
function __construct()
{
// code...
}
function validateIp($ip = '0.0.0.0'){
if (!filter_var($ip, FILTER_VALIDATE_IP)){
return false;
}
}
}

View File

@@ -2,6 +2,7 @@
/** /**
* Notification Manager * Notification Manager
*/ */
//TODO: Working timestamp to body or $title
class NotificationManager class NotificationManager
{ {
function addSubscriber($userID = '', $token = ''){ function addSubscriber($userID = '', $token = ''){
@@ -15,11 +16,11 @@ class NotificationManager
} }
} }
function getSubscription(){ function getSubscription () {
return Db::loadAll('SELECT * FROM notifications;', array()); return Db::loadAll ("SELECT * FROM notifications");
} }
function sendSimpleNotification(string $serverKey, string $to, array $data){ function sendSimpleNotification(string $serverKey, string $to, array $data, bool $timeStamp = false){
$dataTemplate = [ $dataTemplate = [
'title' => '', 'title' => '',
'body' => '', 'body' => '',
@@ -30,6 +31,10 @@ class NotificationManager
return; return;
} }
if ($timeStamp) {
$data['title'] = $data['title'] . date();
}
$notification = new Notification($serverKey); $notification = new Notification($serverKey);
$notification->to($to); $notification->to($to);
$notification->notification($data['title'], $data['body'], $data['icon'], ''); $notification->notification($data['title'], $data['body'], $data['icon'], '');
@@ -64,8 +69,12 @@ class Notification
$this->jsonPayload["to"] = $to; $this->jsonPayload["to"] = $to;
} }
function notification($title = '', $body = '', $icon = '', $action = '') function notification($title = '', $body = '', $icon = '', $action = '', bool $timeStamp = false)
{ {
if ($timeStamp) {
$data['title'] = $data['title'] . date();
}
$this->jsonPayload["data"]["notification"]["title"] = $title; $this->jsonPayload["data"]["notification"]["title"] = $title;
$this->jsonPayload["data"]["notification"]["body"] = $body; $this->jsonPayload["data"]["notification"]["body"] = $body;
$this->jsonPayload["data"]["notification"]["icon"] = $icon; $this->jsonPayload["data"]["notification"]["icon"] = $icon;

View File

@@ -67,7 +67,7 @@ class RecordManager{
public static function clean ($day) { public static function clean ($day) {
if (isset($day)) { if (isset($day)) {
Db::command ('DELETE FROM records WHERE time < ADDDATE(NOW(), INTERVAL -? DAY);', array($day)); Db::command ('DELETE FROM records WHERE `time` < ADDDATE(NOW(), INTERVAL -? DAY);', array($day));
} }
} }

View File

@@ -2,6 +2,11 @@
class RoomManager{ class RoomManager{
public static $rooms; public static $rooms;
function getDefaultRoomId() {
$defaultRoom = Db::loadOne("SELECT room_id FROM rooms WHERE 'default' = 1");
return $defaultRoom['room_id'];
}
function getAllRooms () { function getAllRooms () {
$allRoom = Db::loadAll ("SELECT rooms.*, COUNT(devices.device_id) as device_count FROM rooms LEFT JOIN devices ON (devices.room_id=rooms.room_id) GROUP BY rooms.room_id"); $allRoom = Db::loadAll ("SELECT rooms.*, COUNT(devices.device_id) as device_count FROM rooms LEFT JOIN devices ON (devices.room_id=rooms.room_id) GROUP BY rooms.room_id");
return $allRoom; return $allRoom;

View File

@@ -27,7 +27,7 @@ class Template extends Partial{
function render() { function render() {
extract($this->assignedValues); extract($this->assignedValues);
if (!empty('app/controls/' . $this->path . '.php') && file_exists('app/controls/' . $this->path . '.php')) { if (!empty('app/controls/' . $this->path . '.php') && file_exists('app/controls/' . $this->path . '.php')) {
require_once('app/controls/' . $this->path . '.php'); include('app/controls/' . $this->path . '.php');
} }
require_once('app/templates/' . $this->path . '.phtml'); require_once('app/templates/' . $this->path . '.phtml');
} }

View File

@@ -21,6 +21,24 @@ class UserManager
} }
} }
public function getUserId ($userId) {
try {
$user = Db::loadOne ("SELECT * FROM users WHERE user_id = ?", [$userId]);
return $user;
} catch(PDOException $error) {
echo $error->getMessage();
die();
}
}
public function getAvatarUrl($userId = null){
$email = self::getUserData('email');
if ($userId != null){
$email = self::getUserData('email',$userId);
}
return 'https://secure.gravatar.com/avatar/' . md5( strtolower( trim( $email ) ) );
}
public function login ($username, $password, $rememberMe) { public function login ($username, $password, $rememberMe) {
try { try {
if ($user = Db::loadOne ('SELECT * FROM users WHERE LOWER(username)=LOWER(?)', array ($username))) { if ($user = Db::loadOne ('SELECT * FROM users WHERE LOWER(username)=LOWER(?)', array ($username))) {
@@ -102,10 +120,8 @@ class UserManager
} }
public static function getUserData ($type, $userId = '') { public static function getUserData ($type, $userId = '') {
if (isset($_SESSION['user']['id'])) { if ($userId == '') {
$userId = $_SESSION['user']['id']; $userId = $_SESSION['user']['id'];
} else {
return "";
} }
$user = Db::loadOne ('SELECT ' . $type . ' FROM users WHERE user_id=?', array ($userId)); $user = Db::loadOne ('SELECT ' . $type . ' FROM users WHERE user_id=?', array ($userId));
return $user[$type]; return $user[$type];

View File

@@ -56,7 +56,9 @@ class Utilities
'data' => [ 'data' => [
'datasets' => [ 'datasets' => [
[ [
'data' => $data 'data' => $data,
'borderColor' => "#d4def7",
'backgroundColor' => "#d4def7"
] ]
] ]
], ],
@@ -119,7 +121,7 @@ class Utilities
case '>=': // Greater than or equal to case '>=': // Greater than or equal to
return $value1 >= $value2; return $value1 >= $value2;
case '==': // Equal case '==': // Equal
return $value1 == $value2; return ($value1 == $value2);
case '===': // Identical case '===': // Identical
return $value1 === $value2; return $value1 === $value2;
case '!==': // Not Identical case '!==': // Not Identical

View File

@@ -2,22 +2,33 @@
if (isset($_POST) && !empty($_POST)){ if (isset($_POST) && !empty($_POST)){
if (isset($_POST['modalFinal']) && $_POST['action'] == "add") { if (isset($_POST['modalFinal']) && $_POST['action'] == "add") {
$doCode = json_encode($_POST['device'], JSON_PRETTY_PRINT); $doCode = json_encode($_POST['device'], JSON_PRETTY_PRINT);
$value = $_POST['atSelector'];
if ($_POST['atSelector'] == 'time'){
$value = $_POST['atSelectorValue'];
} else if ($_POST['atSelector'] == 'atDeviceValue') {
$value = json_decode($_POST['atSelectorValue']);
} else if ($_POST['atSelector'] == 'inHome' || $_POST['atSelector'] == 'outHome') {
$value = UserManager::getUserData('user_id');
}
$ifCode = json_encode([ $ifCode = json_encode([
"type" => $_POST['atSelector'], "type" => $_POST['atSelector'],
"value" => $_POST['atSelectorValue'], "value" => $value,
], JSON_PRETTY_PRINT); ], JSON_PRETTY_PRINT);
$onDays = $_POST['atDays']; $onDays = $_POST['atDays'];
//Debug //Debug
if (DEBUGMOD == 1) { // if (DEBUGMOD == 1) {
echo '<pre>'; // echo '<pre>';
echo $permissionsInJson; // echo $permissionsInJson;
echo $deviceId; // echo $deviceId;
var_dump(json_decode ($permissionsInJson)); // var_dump(json_decode ($permissionsInJson));
echo '</pre>'; // echo '</pre>';
echo '<a href="' . BASEDIR .'">CONTINUE</a>'; // echo '<a href="' . BASEDIR .'">CONTINUE</a>';
die(); // die();
} // }
AutomationManager::create($_POST['name'], $onDays, $doCode, $ifCode); AutomationManager::create($_POST['name'], $onDays, $doCode, $ifCode);
@@ -32,18 +43,28 @@ if (isset($_POST) && !empty($_POST)){
$subDevice = SubDeviceManager::getSubDevice($subDeviceId); $subDevice = SubDeviceManager::getSubDevice($subDeviceId);
$subDeviceMaster = SubDeviceManager::getSubDeviceMaster($subDeviceId,$subDevice['type']); $subDeviceMaster = SubDeviceManager::getSubDeviceMaster($subDeviceId,$subDevice['type']);
$json = json_encode([ $device = [
'deviceID' => $subDeviceMaster['device_id'], 'deviceID' => $subDeviceMaster['device_id'],
'type'=> $subDevice['type'], 'type'=> $subDevice['type'],
'value'=> $subDeviceValue, 'value'=> $subDeviceValue,
]); ];
} }
$_POST['atSelectorValue'] = (isset($_POST['atTime']) ? $_POST['atTime'] : (isset($_POST['atDeviceValue']) ? $json : $_POST['atSelector'])); $value = $_POST['atSelector'];
if (isset($_POST['atTime'])){
$value = $_POST['atTime'];
} else if (isset($_POST['atDeviceValue'])) {
$value = $device;
} else if ($_POST['atSelector'] == 'inHome' || $_POST['atSelector'] == 'outHome') {
//TODO: opravit edit aby vkládal id původního uživatele
$value = UserManager::getUserData('user_id');
}
$value = (isset($_POST['atTime']) ? $_POST['atTime'] : (isset($_POST['atDeviceValue']) ? $device : $_POST['atSelector']));
$ifCode = json_encode([ $ifCode = json_encode([
"type" => $_POST['atSelector'], "type" => $_POST['atSelector'],
"value" => $_POST['atSelectorValue'], "value" => $value,
], JSON_PRETTY_PRINT); ], JSON_PRETTY_PRINT);
$onDays = ($_POST['day'] != '' ? json_encode($_POST['day']) : ''); $onDays = ($_POST['day'] != '' ? json_encode($_POST['day']) : '');

View File

@@ -5,6 +5,20 @@ if (isset($_POST) && !empty($_POST)){
$deviceName = $_POST['deviceName']; $deviceName = $_POST['deviceName'];
$deviceIcon = $_POST['deviceIcon']; $deviceIcon = $_POST['deviceIcon'];
$sleepTime = 0; $sleepTime = 0;
if (isset($_FILES['deviceFirmware']) && isset($_FILES['deviceFirmware']['tmp_name']) && $_FILES['deviceFirmware']['tmp_name'] != "") {
$file = $_FILES['deviceFirmware'];
$deviceMac = DeviceManager::getDeviceById($deviceId)['mac'];
$fileName = (isset ($deviceMac) && $deviceMac != "" ? str_replace(":", "", $deviceMac) . ".bin" : "");
if ($fileName != "" && file_exists("./app/updater/" . $fileName)) {
unlink("./app/updater/" . $fileName);
}
if ($fileName != "") {
copy($file['tmp_name'], "./app/updater/" . $fileName);
} else {
}
}
if (isset($_POST['sleepTime'])) { if (isset($_POST['sleepTime'])) {
$sleepTime = $_POST['sleepTime']; $sleepTime = $_POST['sleepTime'];
} }

View File

@@ -28,6 +28,7 @@ return $lang = [
'b_restart' => 'Restart', 'b_restart' => 'Restart',
'b_disable' => 'Deaktivovat', 'b_disable' => 'Deaktivovat',
'b_select' => 'Zvolit', 'b_select' => 'Zvolit',
'b_ota' => 'ota',
//labels //labels
'l_choseDevice' => 'Zvolte zařízení:', 'l_choseDevice' => 'Zvolte zařízení:',
@@ -57,6 +58,10 @@ return $lang = [
'l_password' => 'Heslo', 'l_password' => 'Heslo',
'l_oldPassword' => 'Staré Heslo', 'l_oldPassword' => 'Staré Heslo',
'l_newPassword' => 'Nové Heslo', 'l_newPassword' => 'Nové Heslo',
'l_uploadFirmware' => 'Nahrát Firmware',
'l_userAvatar' => 'Avatar',
'l_userEmail' => 'Email',
'l_roomName' => 'Jméno Místnosti',
//Title //Title
't_createScene' => 'Vytvořit scénu', 't_createScene' => 'Vytvořit scénu',
@@ -70,6 +75,14 @@ return $lang = [
't_experimental' => 'Experimental', 't_experimental' => 'Experimental',
't_createuser' => 'Vytvořit Uživatele', 't_createuser' => 'Vytvořit Uživatele',
't_changePassword' => 'Změnit Heslo', 't_changePassword' => 'Změnit Heslo',
't_networkSetting' => 'Nastavení Sítě',
't_deviceVersion' => 'Nastavení Verze',
't_ota' => 'OTA',
't_listUsers' => 'Seznam Uživatelů',
't_avatar' => 'Avatar',
't_listRooms' => 'Seznam Místností',
't_roomName' => 'Jméno Místnosti',
't_createRoom' => 'Vytvořit Místnost',
//constants //constants
'temp' => 'Teplota', 'temp' => 'Teplota',

View File

@@ -28,6 +28,7 @@ return $lang = [
'b_restart' => 'Restart', 'b_restart' => 'Restart',
'b_disable' => 'disabele', 'b_disable' => 'disabele',
'b_select' => 'Select', 'b_select' => 'Select',
'b_ota' => 'ota',
//labels //labels
'l_choseDevice' => 'Chose device:', 'l_choseDevice' => 'Chose device:',
@@ -57,6 +58,10 @@ return $lang = [
'l_password' => 'Password', 'l_password' => 'Password',
'l_oldPassword' => 'Old Password', 'l_oldPassword' => 'Old Password',
'l_newPassword' => 'New Password', 'l_newPassword' => 'New Password',
'l_uploadFirmware' => 'Upload Firmware',
'l_userAvatar' => 'Avatar',
'l_userEmail' => 'Email',
'l_roomName' => 'Room Name',
//Title //Title
't_createScene' => 'Create Scene', 't_createScene' => 'Create Scene',
@@ -70,6 +75,14 @@ return $lang = [
't_experimental' => 'Experimental', 't_experimental' => 'Experimental',
't_createuser' => 'Create User', 't_createuser' => 'Create User',
't_changePassword' => 'Change Password', 't_changePassword' => 'Change Password',
't_networkSetting' => 'Network Setting',
't_deviceVersion' => 'Version Setting',
't_ota' => 'OTA',
't_listUsers' => 'User List',
't_avatar' => 'Avatar',
't_listRooms' => 'Room List',
't_roomName' => 'Room Name',
't_createRoom' => 'Create Rom',
//constants //constants
'humi' => 'Humidity', 'humi' => 'Humidity',

View File

@@ -16,6 +16,7 @@
$partial = new Partial('menu'); $partial = new Partial('menu');
$partial->prepare('item','automation'); $partial->prepare('item','automation');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('debugMod',$DEBUGMOD);
$partial->render(); $partial->render();
?> ?>
</div> </div>
@@ -29,10 +30,11 @@
$partial->prepare('automationId',$automationId); $partial->prepare('automationId',$automationId);
$partial->prepare('automationData',$automationData); $partial->prepare('automationData',$automationData);
$partial->render(); $partial->render();
//EDIT //EDIT
$partial = new Partial('automationEdit'); $partial = new Partial('automationEdit');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('userManager',$USERMANAGER);
$partial->prepare('automationId',$automationId); $partial->prepare('automationId',$automationId);
$partial->prepare('automation',$automationData); $partial->prepare('automation',$automationData);
$partial->prepare('subDevices',$SUBDEVICES); $partial->prepare('subDevices',$SUBDEVICES);
@@ -41,15 +43,17 @@
</div> </div>
</div> </div>
</div> </div>
<?php <?php
if (isset($_POST['modalNext'])) { if (isset($_POST['modalNext'])) {
$partial = new Partial('automationCreateFinal'); $partial = new Partial('automationCreateFinal');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('userManager',$USERMANAGER);
$partial->prepare('subDevices',$SUBDEVICES); $partial->prepare('subDevices',$SUBDEVICES);
$partial->render(); $partial->render();
} else { } else {
$partial = new Partial('automationCreate'); $partial = new Partial('automationCreate');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('subDevices',$SUBDEVICES); $partial->prepare('subDevices',$SUBDEVICES);
$partial->render(); $partial->render();
}?> }?>

View File

@@ -13,4 +13,9 @@ table.table th {
text-align: left; text-align: left;
background-color: #121a2b; background-color: #121a2b;
color: white; color: white;
} }
button:disabled,
button[disabled] {
opacity: .4;
}

View File

@@ -16,6 +16,7 @@
$partial = new Partial('menu'); $partial = new Partial('menu');
$partial->prepare('item', 'dashboard'); $partial->prepare('item', 'dashboard');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('debugMod',$DEBUGMOD);
$partial->render(); $partial->render();
?> ?>
</div> </div>
@@ -25,13 +26,13 @@
<?php foreach ($DASHBOARD as $dashboardItemId => $dashboardItemData) { <?php foreach ($DASHBOARD as $dashboardItemId => $dashboardItemData) {
$partialDeviceButton = new Partial('dashboardButton'); $partialDeviceButton = new Partial('dashboardButton');
$partialDeviceButton->prepare('dashboardItemData', $dashboardItemData); $partialDeviceButton->prepare('dashboardItemData', $dashboardItemData);
$partialDeviceButton->render(); $partialDeviceButton->render();
} ?> } ?>
</div> </div>
</div> </div>
</div> </div>
<div class="modal-container modal-container-hiden" id="modal"> <div class="modal-container modal-container-hiden" id="modal">
<div class="modal"> <div class="modal">
<div class="close"> <div class="close">
@@ -51,12 +52,12 @@
</form> </form>
</div> </div>
</div> </div>
<?php <?php
if (isset($_POST['deviceId'])) { if (isset($_POST['deviceId'])) {
$partial = new Partial('deviceEdit'); $partial = new Partial('deviceEdit');
$partial->prepare('DEVICEDATA', $DEVICEDATA); $partial->prepare('DEVICEDATA', $DEVICEDATA);
$partial->render(); $partial->render();
} }
$partial = new Partial('footer'); $partial = new Partial('footer');

View File

@@ -16,18 +16,19 @@
$partial = new Partial('menu'); $partial = new Partial('menu');
$partial->prepare('item', 'home'); $partial->prepare('item', 'home');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('debugMod',$DEBUGMOD);
$partial->render(); $partial->render();
?> ?>
</div> </div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.7.3/Chart.bundle.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.7.3/Chart.bundle.min.js"></script>
<div class="col-md-9 main-body"> <div class="col-md-9 main-body">
<div class="label m-1"> <div class="label m-1">
<?php <?php
if ($USERSATHOME != "") { if ($USERSATHOME != "") {
$LANGMNG->echo('l_atHome'); $LANGMNG->echo('l_atHome');
echo ': ' . $USERSATHOME; echo ': ' . $USERSATHOME;
} }
?> ?>
</div> </div>
@@ -42,8 +43,8 @@
</select> </select>
</div> </div>
<div class="row no-gutters"> <div class="row no-gutters">
<?php foreach ($DATA as $roomId => $room) { ?> <?php foreach ($DATA as $roomId => $room) { ?>
<?php foreach ($room['devices'] as $deviceId => $device) { ?> <?php foreach ($room['devices'] as $deviceId => $device) { ?>
<?php foreach ($device['subDevices'] as $subDeviceKey => $subDevice) { <?php foreach ($device['subDevices'] as $subDeviceKey => $subDevice) {
//BUTTON //BUTTON
$partialDeviceButton = new Partial('deviceButton'); $partialDeviceButton = new Partial('deviceButton');
@@ -52,18 +53,18 @@
$partialDeviceButton->prepare('subdevice',$subDevice); $partialDeviceButton->prepare('subdevice',$subDevice);
$partialDeviceButton->prepare('deviceid',$deviceId); $partialDeviceButton->prepare('deviceid',$deviceId);
$partialDeviceButton->prepare('device',$device); $partialDeviceButton->prepare('device',$device);
$partialDeviceButton->render(); $partialDeviceButton->render();
//DETAIL //DETAIL
$partialDetail = new Partial('deviceDetail'); $partialDetail = new Partial('deviceDetail');
$partialDetail->prepare('subdeviceid',$subDeviceKey); $partialDetail->prepare('subdeviceid',$subDeviceKey);
$partialDetail->prepare('subdevice',$subDevice); $partialDetail->prepare('subdevice',$subDevice);
$partialDetail->prepare('device',$device); $partialDetail->prepare('device',$device);
$partialDetail->prepare('langMng',$LANGMNG); $partialDetail->prepare('langMng',$LANGMNG);
$partialDetail->render(); $partialDetail->render();
//SETTING //SETTING
$partialEdit = new Partial('deviceEdit'); $partialEdit = new Partial('deviceEdit');
$partialEdit->prepare('deviceid',$deviceId); $partialEdit->prepare('deviceid',$deviceId);
@@ -72,9 +73,9 @@
$partialEdit->prepare('users',$USERS); $partialEdit->prepare('users',$USERS);
$partialEdit->prepare('rooms',$ROOMS); $partialEdit->prepare('rooms',$ROOMS);
$partialEdit->prepare('langMng',$LANGMNG); $partialEdit->prepare('langMng',$LANGMNG);
$partialEdit->render(); $partialEdit->render();
} }
} }
} ?> } ?>
</div> </div>
@@ -85,4 +86,4 @@
$partial->render(); $partial->render();
?> ?>
</body> </body>
</html> </html>

View File

@@ -17,23 +17,24 @@ if ('serviceWorker' in navigator) {
navigator.serviceWorker.register('serviceWorker.js') navigator.serviceWorker.register('serviceWorker.js')
.then(registration => { .then(registration => {
console.log('Service Worker is registered', registration); console.log('Service Worker is registered', registration);
messaging.useServiceWorker(registration); messaging.useServiceWorker(registration);
messaging.usePublicVapidKey('BDYQ7X7J7PX0aOFNqB-CivQeqLq4-SqCxQJlDfJ6yNnQeYRoK8H2KOqxHRh47fLrbUhC8O3tve67MqJAIqox7Ng'); messaging.usePublicVapidKey('BDYQ7X7J7PX0aOFNqB-CivQeqLq4-SqCxQJlDfJ6yNnQeYRoK8H2KOqxHRh47fLrbUhC8O3tve67MqJAIqox7Ng');
messaging.requestPermission().then(function () { messaging.requestPermission().then(function () {
console.log("Notification permission granted."); console.log("Notification permission granted.");
return messaging.getToken() return messaging.getToken()
}) })
.then(function(token) { .then(function (token) {
console.log("token is : " + token); console.log("token is : " + token);
$.ajax({ $.ajax({
url: 'ajax', url: 'ajax',
type: 'POST', type: 'POST',
data: { data: {
"notification" : 'X', "notification": 'X',
"action": 'subscribe', "action": 'subscribe',
"token": token "token": token
}, },
success: function(data){ success: function (data) {
console.log('saved', data); console.log('saved', data);
}, },
error: function (request, status, error) { error: function (request, status, error) {
@@ -44,15 +45,6 @@ if ('serviceWorker' in navigator) {
.catch(function (err) { .catch(function (err) {
console.log("Unable to get permission to notify.", err); console.log("Unable to get permission to notify.", err);
}); });
messaging.onMessage(function(payload) {
console.log("Message received. ", payload);
var notification = new Notification('hello', {
body: "Hey there!",
});
notification.onclick = function () {
window.open("http://google.com");
};
});
}) })
.catch(err => { .catch(err => {
console.error('Registration failed:', err); console.error('Registration failed:', err);
@@ -61,27 +53,27 @@ if ('serviceWorker' in navigator) {
} }
$('select[name="atSelector"]').change(function(e) { $('select[name="atSelector"]').change(function (e) {
console.log($(this).val()); console.log($(this).val());
if( $(this).val() == 'time') { if ($(this).val() == 'time') {
$('input[name="atTime"]').prop( "disabled", false ); $('input[name="atTime"]').prop("disabled", false);
$('select[name="atDeviceValueInt"]').prop( "disabled", true ); $('select[name="atDeviceValueInt"]').prop("disabled", true);
$('input[name="atDeviceValue"]').prop( "disabled", true ); $('input[name="atDeviceValue"]').prop("disabled", true);
} else if( $(this).val() == 'atDeviceValue') { } else if ($(this).val() == 'atDeviceValue') {
$('select[name="atDeviceValue"]').prop( "disabled", false ); $('select[name="atDeviceValue"]').prop("disabled", false);
$('input[name="atDeviceValueInt"]').prop( "disabled", false ); $('input[name="atDeviceValueInt"]').prop("disabled", false);
$('input[name="atTime"]').prop( "disabled", true ); $('input[name="atTime"]').prop("disabled", true);
} }
}); });
var pressTimer; var pressTimer;
var touch = 0; var touch = 0;
var touchSubId = ""; var touchSubId = "";
$("div.square-content").on('touchend', function (e){ $("div.square-content").on('touchend', function (e) {
clearTimeout(pressTimer); clearTimeout(pressTimer);
}); });
@@ -103,10 +95,10 @@ $("div.square-content").on('touchstart', function (eTarget) {
var subId = $(this).attr('data-sub-device-id'); var subId = $(this).attr('data-sub-device-id');
touch++; touch++;
if(touch == 2 && touchSubId == subId){ if (touch == 2 && touchSubId == subId) {
console.log("Detail"); console.log("Detail");
if (windowLoc == "/") { if (windowLoc == "/") {
$("#modal-detail-"+subId).removeClass('modal-container-hiden').show(); $("#modal-detail-" + subId).removeClass('modal-container-hiden').show();
ajaxChart(subId); ajaxChart(subId);
} else if (windowLoc == "/scene") { } else if (windowLoc == "/scene") {
@@ -120,12 +112,12 @@ $("div.square-content").on('touchstart', function (eTarget) {
pressTimer = window.setTimeout(function (e) { pressTimer = window.setTimeout(function (e) {
console.log("Setting"); console.log("Setting");
$("#modal-setting-"+id).removeClass('modal-container-hiden').show(); $("#modal-setting-" + id).removeClass('modal-container-hiden').show();
touch = 0; touch = 0;
}, 500); }, 500);
}); });
$("div.square-content").mousedown(function(e) { $("div.square-content").mousedown(function (e) {
if (event.which == 3) { if (event.which == 3) {
var windowLoc = $(location).attr('pathname'); var windowLoc = $(location).attr('pathname');
windowLoc = windowLoc.substring(windowLoc.lastIndexOf("/")); windowLoc = windowLoc.substring(windowLoc.lastIndexOf("/"));
@@ -138,7 +130,7 @@ $("div.square-content").mousedown(function(e) {
} else if (windowLoc == "/automation") { } else if (windowLoc == "/automation") {
id = $(this).attr('id').replace('automation-', ''); id = $(this).attr('id').replace('automation-', '');
} }
$("#modal-setting-"+id).removeClass('modal-container-hiden').show(); $("#modal-setting-" + id).removeClass('modal-container-hiden').show();
console.log("Setting"); console.log("Setting");
console.log("modal" + id); console.log("modal" + id);
} }
@@ -149,7 +141,7 @@ $(".close").on('click', function (e) {
a.hide(); a.hide();
}); });
$(this).bind("contextmenu", function(e) { $(this).bind("contextmenu", function (e) {
e.preventDefault(); e.preventDefault();
}); });
@@ -159,11 +151,11 @@ $("div.square-content").on('dblclick', function (eTarget) {
console.log("Detail"); console.log("Detail");
var subId = $(this).attr('data-sub-device-id'); var subId = $(this).attr('data-sub-device-id');
ajaxChart(subId); ajaxChart(subId);
$("#modal-detail-"+subId).removeClass('modal-container-hiden').show(); $("#modal-detail-" + subId).removeClass('modal-container-hiden').show();
} }
}); });
$("input#sleepTime").change(function() { $("input#sleepTime").change(function () {
console.log("Input text changed!"); console.log("Input text changed!");
}); });
@@ -175,7 +167,7 @@ $("a#remove").on('click', function (e) {
element.toggle(); element.toggle();
}); });
function ajaxChart(id, period = 'day', group = 'hour'){ function ajaxChart(id, period = 'day', group = 'hour') {
$.ajax({ $.ajax({
url: 'ajax', url: 'ajax',
type: 'POST', type: 'POST',
@@ -186,9 +178,9 @@ function ajaxChart(id, period = 'day', group = 'hour'){
"period": period, "period": period,
"group": group "group": group
}, },
success: function(data){ success: function (data) {
console.log('ID: ',id, 'DATA: ', data); console.log('ID: ', id, 'DATA: ', data);
var ctx = document.getElementById('canvas-'+id).getContext('2d'); var ctx = document.getElementById('canvas-' + id).getContext('2d');
var myChart = new Chart(ctx, data); var myChart = new Chart(ctx, data);
}, },
error: function (request, status, error) { error: function (request, status, error) {
@@ -210,11 +202,11 @@ if (windowLoc == "/") {
} }
console.log('Saved Selected Room ID '+ selectRoomId); console.log('Saved Selected Room ID ' + selectRoomId);
$('[name="room"]').val(selectRoomId); $('[name="room"]').val(selectRoomId);
$('.device-button').each(function(){ $('.device-button').each(function () {
if (selectRoomId != 'all'){ if (selectRoomId != 'all') {
if($(this).data('room-id') != selectRoomId){ if ($(this).data('room-id') != selectRoomId) {
$(this).hide(); $(this).hide();
} else { } else {
$(this).show(); $(this).show();
@@ -226,58 +218,62 @@ if (windowLoc == "/") {
} }
//Room selector //Room selector
$( '[name="room"]' ).change(function (e) { $('[name="room"]').change(function (e) {
console.log('Selected Room ID ' + this.value) console.log('Selected Room ID ' + this.value)
var roomId = this.value; var roomId = this.value;
localStorage.setItem("selectedRoomId", roomId); localStorage.setItem("selectedRoomId", roomId);
$('.device-button').show(); $('.device-button').show();
if (roomId != 'all'){ if (roomId != 'all') {
$('.device-button').each(function(){ $('.device-button').each(function () {
if($(this).data('room-id') != roomId){ if ($(this).data('room-id') != roomId) {
$(this).hide(); $(this).hide();
} }
}); });
} }
}); });
/* /*
var windowLoc = $(location).attr('pathname'); var windowLoc = $(location).attr('pathname');
windowLoc = windowLoc.substring(windowLoc.lastIndexOf("/")); windowLoc = windowLoc.substring(windowLoc.lastIndexOf("/"));
console.log(); console.log();
if (windowLoc == "/") { if (windowLoc == "/") {
var autoUpdate = setInterval(function(){ var autoUpdate = setInterval(function(){
if (pending == false) { if (pending == false) {
pending = true; pending = true;
$.ajax({ $.ajax({
url: 'ajax', url: 'ajax',
type: 'POST', type: 'POST',
dataType: 'json', dataType: 'json',
data: { data: {
"action": 'getState' "action": 'getState'
}, },
success: function(data){ success: function(data){
console.log(data); console.log(data);
for (const key in data) { for (const key in data) {
if (data.hasOwnProperty(key)) { if (data.hasOwnProperty(key)) {
const device = data[key]; const device = data[key];
$('[data-sub-device-id="'+key+'"]') $('[data-sub-device-id="'+key+'"]')
.find('.device-button-value') .find('.device-button-value')
.text(device['value']) .text(device['value'])
.attr('title',device['time']) .attr('title',device['time'])
} }
} }
}, },
error: function (request, status, error) { error: function (request, status, error) {
console.log("ERROR ajaxChart():", request, error); console.log("ERROR ajaxChart():", request, error);
}, },
complete: function (){ complete: function (){
pending = false; pending = false;
} }
}); });
} }
},4000); },4000);
}*/ }*/
//Graphs //Graphs
$('.graph-period').on('click', function (e) { $('.graph-period').on('click', function (e) {
var subId = $(this).attr('data-sub-device-id'); var subId = $(this).attr('data-sub-device-id');
@@ -287,7 +283,7 @@ $('.graph-period').on('click', function (e) {
ajaxChart(subId, period, groupBy); ajaxChart(subId, period, groupBy);
}); });
$( "button[name=remove]" ).click(function(e) { $("button[name=remove]").click(function (e) {
if (confirm('Are you shure ?')) { if (confirm('Are you shure ?')) {
var windowLoc = $(location).attr('pathname'); var windowLoc = $(location).attr('pathname');
windowLoc = windowLoc.substring(windowLoc.lastIndexOf("/")); windowLoc = windowLoc.substring(windowLoc.lastIndexOf("/"));
@@ -295,7 +291,7 @@ $( "button[name=remove]" ).click(function(e) {
var id = null; var id = null;
if (windowLoc == "/scene") { if (windowLoc == "/scene") {
id = $(this).data('scene-id'); id = $(this).data('scene-id');
$("#scene-"+id+"-content").remove(); $("#scene-" + id + "-content").remove();
} else if (windowLoc == "/automation") { } else if (windowLoc == "/automation") {
$(this).parent().remove(); $(this).parent().remove();
} }

View File

@@ -16,11 +16,13 @@
$partial = new Partial('menu'); $partial = new Partial('menu');
$partial->prepare('item', 'log'); $partial->prepare('item', 'log');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('debugMod',$DEBUGMOD);
$partial->render(); $partial->render();
?> ?>
</div> </div>
<div class="col-md-9 main-body"> <div class="col-md-9 main-body">
<div class="col-12 col-sm-9 mx-auto mt-4"> <div class="col-12 col-sm-9 mx-auto mt-4">
<label><?php echo $LANGMNG->get('l_logMaxLiveTime') . " " . $LOGTOLIVETIME . " days";?></label>
<form method="post" action=""> <form method="post" action="">
<div class="field"> <div class="field">
<select class="input" name="LogFile"> <select class="input" name="LogFile">
@@ -33,7 +35,7 @@
<input type="submit" class="button" name="selectFile" value="<?php $LANGMNG->echo('b_select');?>"/> <input type="submit" class="button" name="selectFile" value="<?php $LANGMNG->echo('b_select');?>"/>
</div> </div>
</form> </form>
<?php <?php
if (isset($_POST['LogFile'])) { if (isset($_POST['LogFile'])) {
$file_lines = file('./app/logs/' . $_POST['LogFile']); $file_lines = file('./app/logs/' . $_POST['LogFile']);
echo '<pre style="overflow: auto;">'; echo '<pre style="overflow: auto;">';
@@ -45,7 +47,7 @@
?> ?>
</div> </div>
</div> </div>
<?php <?php
$partial = new Partial('footer'); $partial = new Partial('footer');
$partial->render(); $partial->render();

View File

@@ -50,6 +50,12 @@
<div class="col"> <div class="col">
<?php echo implode(', ',$AUTOMATIONDATA['onDays']);?> <?php echo implode(', ',$AUTOMATIONDATA['onDays']);?>
</div> </div>
<div class="col">
<?php echo $AUTOMATIONDATA['owner_name'];?>
</div>
<div class="col">
<?php echo $AUTOMATIONDATA['execution_time'];?>
</div>
</div> </div>
<div class="row"> <div class="row">
<div class="col"> <div class="col">

View File

@@ -2,7 +2,7 @@
<div class="modal"> <div class="modal">
<a href=""><i class="fa fa-times close"></i></a> <a href=""><i class="fa fa-times close"></i></a>
<h4 class="mb-4"><?php $LANGMNG->echo('t_createAutomation')?></h4> <h4 class="mb-4"><?php $LANGMNG->echo('t_createAutomation')?></h4>
<form method="post"> <form method="post" action="" >
<div class="field"> <div class="field">
<div class="label"><?php $LANGMNG->echo('l_nameAt')?></div> <div class="label"><?php $LANGMNG->echo('l_nameAt')?></div>
<div class="field"> <div class="field">

View File

@@ -21,9 +21,12 @@
'value'=> $subDeviceValue, 'value'=> $subDeviceValue,
]); ]);
echo htmlspecialchars($json); echo htmlspecialchars($json);
} } else {
else { if ($_POST['atSelector'] == "inHome" || $_POST['atSelector'] == "outHome") {
echo $_POST['atSelector']; echo $USERMANAGER->getUserData('user_id');
} else {
echo $_POST['atSelector'];
}
} ?>" required/> } ?>" required/>
<input type="hidden" name="atDays" value="<?php echo htmlspecialchars(($_POST['day'] != '' ? json_encode($_POST['day']) : '')); ?>" required/> <input type="hidden" name="atDays" value="<?php echo htmlspecialchars(($_POST['day'] != '' ? json_encode($_POST['day']) : '')); ?>" required/>
<?php foreach ($_POST['devices'] as $value) { ?> <?php foreach ($_POST['devices'] as $value) { ?>

View File

@@ -62,9 +62,6 @@
<thead> <thead>
<tr> <tr>
<th><?php $LANGMNG->echo('t_time');?></th> <th><?php $LANGMNG->echo('t_time');?></th>
<?php if (DEBUGMOD) { ?>
<th><?php $LANGMNG->echo('t_raw');?></th>
<?php } ?>
<th><?php $LANGMNG->echo('t_state');?></th> <th><?php $LANGMNG->echo('t_state');?></th>
</tr> </tr>
</thead> </thead>
@@ -72,10 +69,12 @@
<?php foreach ($SUBDEVICE['events'] as $key => $value) { ?> <?php foreach ($SUBDEVICE['events'] as $key => $value) { ?>
<tr> <tr>
<td><?php echo (new DateTime($value['time']))->format(DATEFORMAT); ?></td> <td><?php echo (new DateTime($value['time']))->format(DATEFORMAT); ?></td>
<?php if (DEBUGMOD) { ?> <td title="test"><?php
<td><?php echo $SUBDEVICE['eventsRaw'][$key]['value']; ?></td> echo $value['value'] . $SUBDEVICE['unit'];
<?php } ?> if (DEBUGMOD) {
<td title="test"><?php echo $value['value'] . $SUBDEVICE['unit'];?></td> echo ' (' . $SUBDEVICE['eventsRaw'][$key]['value'] . ')';
}
?></td>
<?php //TODO: P5IDAT TOOLTIP PRO RAW VALUE?> <?php //TODO: P5IDAT TOOLTIP PRO RAW VALUE?>
</tr> </tr>
<?php } ?> <?php } ?>

View File

@@ -4,7 +4,7 @@
<i class="fa fa-times"></i> <i class="fa fa-times"></i>
</div> </div>
<h4 class="mb-4"><?php $LANGMNG->echo('t_editDevice'); ?></h4> <h4 class="mb-4"><?php $LANGMNG->echo('t_editDevice'); ?></h4>
<form method="post" action=""> <form method="post" action="" enctype="multipart/form-data">
<input class="input" type="hidden" name="deviceId" value="<?php echo $DEVICEID; ?>"> <input class="input" type="hidden" name="deviceId" value="<?php echo $DEVICEID; ?>">
<?php if ($DEVICE['approved'] != 0) { ?> <?php if ($DEVICE['approved'] != 0) { ?>
<?php if ($DEVICE['userIsAdmin']) { ?> <?php if ($DEVICE['userIsAdmin']) { ?>
@@ -12,7 +12,7 @@
<div class="label"><?php $LANGMNG->echo('l_owner'); ?></div> <div class="label"><?php $LANGMNG->echo('l_owner'); ?></div>
<select class="input" name="deviceOwnerUserId"> <select class="input" name="deviceOwnerUserId">
<option value=""><?php $LANGMNG->echo('w_noOne'); ?></option> <option value=""><?php $LANGMNG->echo('w_noOne'); ?></option>
<?php foreach ($USERS as $user) { <?php foreach ($USERS as $user) {
$userId = $user['user_id']; $userId = $user['user_id'];
$userName = $user['username']; $userName = $user['username'];
?> ?>
@@ -22,13 +22,13 @@
</div> </div>
<div class="label"><?php $LANGMNG->echo('l_permission'); ?></div> <div class="label"><?php $LANGMNG->echo('l_permission'); ?></div>
<div class="row"> <div class="row">
<div class="col-6"> <div class="col-6">
<div class="label"> - <?php $LANGMNG->echo('l_owner'); ?></div> <div class="label"> - <?php $LANGMNG->echo('l_owner'); ?></div>
</div> </div>
<div class="col-6"> <div class="col-6">
<?php <?php
$permissions = $DEVICE['permission']; $permissions = $DEVICE['permission'];
//Debug //Debug
if (DEBUGMOD == 1) { if (DEBUGMOD == 1) {
@@ -40,7 +40,7 @@
<input type="radio" name="permissionOwner" value=1 <?php ECHO ($permissions[0] == 1 ? 'checked' : ''); ?>/><?php $LANGMNG->echo('l_read'); ?> <input type="radio" name="permissionOwner" value=1 <?php ECHO ($permissions[0] == 1 ? 'checked' : ''); ?>/><?php $LANGMNG->echo('l_read'); ?>
<input type="radio" name="permissionOwner" value=2 <?php ECHO ($permissions[0] == 2 ? 'checked' : ''); ?>/><?php $LANGMNG->echo('l_use'); ?> <input type="radio" name="permissionOwner" value=2 <?php ECHO ($permissions[0] == 2 ? 'checked' : ''); ?>/><?php $LANGMNG->echo('l_use'); ?>
<input type="radio" name="permissionOwner" value=3 <?php ECHO ($permissions[0] == 3 ? 'checked' : ''); ?>/><?php $LANGMNG->echo('l_edit'); ?> <input type="radio" name="permissionOwner" value=3 <?php ECHO ($permissions[0] == 3 ? 'checked' : ''); ?>/><?php $LANGMNG->echo('l_edit'); ?>
</div> </div>
</div> </div>
<div class="row"> <div class="row">
@@ -60,22 +60,50 @@
<?php } ?> <?php } ?>
<div class="field"> <div class="field">
<div class="label">Token:</div> <div class="label">Token:</div>
<input class="input" type="text" name="deviceToken" value="<?php echo $DEVICE['token']; ?>" disabled> <input class="input" type="text" name="deviceToken" value="<?php echo $DEVICE['token']; ?>" disabled>
</div> </div>
<h4 class="mb-4"><?php $LANGMNG->echo('t_networkSetting'); ?></h4>
<div class="field">
<div class="label">Type:</div>
<input class="input" type="text" name="deviceToken" value="<?php echo $DEVICE['type']; ?>" disabled>
</div>
<div class="field">
<div class="label">Mac Address:</div>
<input class="input" type="text" name="deviceMac" value="<?php echo $DEVICE['mac']; ?>" disabled>
</div>
<div class="field">
<div class="label">IP:</div>
<input class="input" type="text" name="deviceIp" value="<?php echo $DEVICE['ip']; ?>" minlength="7" maxlength="15" size="15" pattern="^((\d{1,2}|1\d\d|2[0-4]\d|25[0-5])\.){3}(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])$" disabled>
</div>
<div class="field">
<div class="label">Subnet:</div>
<input class="input" type="text" name="deviceSubnet" value="<?php echo $DEVICE['subnet']; ?>" minlength="7" maxlength="15" size="15" pattern="^((\d{1,2}|1\d\d|2[0-4]\d|25[0-5])\.){3}(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])$" disabled>
</div>
<div class="field">
<div class="label">Gateway:</div>
<input class="input" type="text" name="deviceGateway" value="<?php echo $DEVICE['gateway']; ?>" minlength="7" maxlength="15" size="15" pattern="^((\d{1,2}|1\d\d|2[0-4]\d|25[0-5])\.){3}(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])$" disabled>
</div>
<h4 class="mb-4"><?php $LANGMNG->echo('t_deviceVersion'); ?></h4>
<div class="field">
<div class="label"><?php $LANGMNG->echo('l_uploadFirmware'); ?></div>
<input class="input" type="file" name="deviceFirmware" value="">
</div>
<?php if ($DEVICE['userIsAdmin']) { ?> <?php if ($DEVICE['userIsAdmin']) { ?>
<?php if (!in_array($SUBDEVICE['type'], ['on/off', 'door', 'water'])) { ?> <?php if (!in_array($SUBDEVICE['type'], ['on/off', 'door', 'water'])) { ?>
<div class="field"> <div class="field">
<div class="label"><?php $LANGMNG->echo('l_sleepTime'); ?></div> <div class="label"><?php $LANGMNG->echo('l_sleepTime'); ?></div>
<input class="input" type="int" name="sleepTime" value="<?php echo $DEVICE['sleepTime']; ?>" <?php echo (!$DEVICE['userIsAdmin'] ? 'disabled' : ''); ?>> <input class="input" type="int" name="sleepTime" value="<?php echo $DEVICE['sleepTime']; ?>" <?php echo (!$DEVICE['userIsAdmin'] ? 'disabled' : ''); ?>>
<p>* - <?php $LANGMNG->echo('l_inMinutes'); ?></p> <p>* - <?php $LANGMNG->echo('l_inMinutes'); ?></p>
</div> </div>
<?php }?> <?php }?>
<div class="field"> <div class="field">
<div class="label"><?php $LANGMNG->echo('w_room'); ?></div> <div class="label"><?php $LANGMNG->echo('w_room'); ?></div>
<select class="input" name="deviceOwnerId"> <select class="input" name="deviceOwnerId">
<?php foreach ($ROOMS as $room) { <?php foreach ($ROOMS as $room) {
$roomId = $room['room_id']; $roomId = $room['room_id'];
$roomName = $room['name']; $roomName = $room['name'];
?> ?>
<option value="<?php echo $roomId; ?>" <?php ECHO ((int) $roomId === (int) $DEVICE['room'] ? 'selected="selected"' : ''); ?>><?php echo $roomName; ?></option> <option value="<?php echo $roomId; ?>" <?php ECHO ((int) $roomId === (int) $DEVICE['room'] ? 'selected="selected"' : ''); ?>><?php echo $roomName; ?></option>
<?php } ?> <?php } ?>
@@ -101,26 +129,26 @@
<div class="label"><?php $LANGMNG->echo('w_moduls'); ?></div> <div class="label"><?php $LANGMNG->echo('w_moduls'); ?></div>
<div class="row no-gutters"> <div class="row no-gutters">
<?php foreach ($DEVICE['subDevices'] as $subDeviceKey => $subDevice) { ?> <?php foreach ($DEVICE['subDevices'] as $subDeviceKey => $subDevice) { ?>
<div class="col-4 col-sm-3 col-xl-2 square-wrap"> <div class="device-button col-4 col-sm-3 col-xl-2 square-wrap">
<div class="square"> <div class="square">
<div class="square-content"> <div class="square-content">
<div class="row"> <div class="row no-gutters">
<div class="col"> <div class="col">
<h3 class="fa">&#x<?php echo $DEVICE['icon']; ?></h3> <h5 unselectable="on" class="fa">&#x<?php echo $DEVICE['icon'] ?></h5>
</div> </div>
<div class="col"> <div class="col">
<h3><?php echo $subDevice['unit']; ?></h3> <h5 unselectable="on" class="device-button-value text-right" title="<?php echo $subDevice['lastRecort']['time']; ?>"><?php echo $subDevice['lastRecort']['value'] . $subDevice['unit']?></h5>
</div> </div>
</div> </div>
<div class="row"> <div class="row">
<div class="col"> <div class="col button-text" unselectable="on" >
<?php echo $DEVICE['name']; ?> <?php echo $DEVICE['name']; ?>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
<?php } ?> <?php } ?>
</div> </div>
</div> </div>
<input type="submit" class="button" name="saveDevice" value="<?php $LANGMNG->echo('b_save'); ?>" <?php echo (!$DEVICE['userIsAdmin'] ? 'disabled' : ''); ?>/> <input type="submit" class="button" name="saveDevice" value="<?php $LANGMNG->echo('b_save'); ?>" <?php echo (!$DEVICE['userIsAdmin'] ? 'disabled' : ''); ?>/>
@@ -130,26 +158,17 @@
<div class="label"><?php $LANGMNG->echo('w_moduls'); ?></div> <div class="label"><?php $LANGMNG->echo('w_moduls'); ?></div>
<div class="row no-gutters"> <div class="row no-gutters">
<?php foreach ($DEVICE['subDevices'] as $subDeviceKey => $subDevice) { ?> <?php foreach ($DEVICE['subDevices'] as $subDeviceKey => $subDevice) { ?>
<div class="col-4 col-sm-3 col-xl-2 square-wrap"> <div class="device-button col-4 col-sm-3 col-xl-2 square-wrap">
<div class="square"> <div class="square">
<div class="square-content"> <div class="square-content">
<div class="row">
<div class="col"> <?php echo $DEVICE['name']; ?>
<h3 class="fa">&#x<?php echo $DEVICE['icon']; ?></h3>
</div>
<div class="col">
<h3><?php echo $subDevice['unit']; ?></h3>
</div>
</div>
<div class="row">
<div class="col">
<?php echo $DEVICE['name']; ?>
</div>
</div>
</div> </div>
</div> </div>
</div> </div>
<?php } ?> <?php } ?>
</div> </div>
</div> </div>
<input type="submit" class="button is-primary" name="approveDevice" value="<?php $LANGMNG->echo('b_approve'); ?>"/> <input type="submit" class="button is-primary" name="approveDevice" value="<?php $LANGMNG->echo('b_approve'); ?>"/>
@@ -157,4 +176,4 @@
<?php } ?> <?php } ?>
</form> </form>
</div> </div>
</div> </div>

View File

@@ -32,7 +32,11 @@
'path' => 'log', 'path' => 'log',
], ],
]; ];
foreach ( $menuItems as $key => $value) { ?> foreach ( $menuItems as $key => $value) {
if ($DEBUGMOD == 0 && $value['path'] == 'log') {
continue;
}
?>
<div class="nav-item <?php echo ($ITEM == $value ? 'is-active' : ''); ?>"> <div class="nav-item <?php echo ($ITEM == $value ? 'is-active' : ''); ?>">
<a href="<?php echo $value['path']?>"> <a href="<?php echo $value['path']?>">
<i class="fa <?php echo $key ?>"></i> <i class="fa <?php echo $key ?>"></i>
@@ -42,5 +46,5 @@
</a> </a>
</div> </div>
<?php }?> <?php }?>
</div> </div>

View File

@@ -1,6 +1,6 @@
<div class="col-12 col-md-6 col-xl-4 square-wrap noselect"> <div class="col-12 col-md-6 col-xl-4 square-wrap noselect">
<div class="rectangle-2"> <div class="rectangle-2">
<div class="square-content double" id="scene-<?php echo $SCENEID ?>" onClick="ajaxPost('ajax',{scene_id:'<?php echo $SCENEID; ?>'}, this);" > <div class="square-content double" id="scene-<?php echo $SCENEID ?>" onClick="ajaxPost('ajax',{scene_id:'<?php echo $SCENEID; ?>',action:'execute'}, this);" >
<div class="row"> <div class="row">
<div class="col-1"> <div class="col-1">
<h5 class="fa noselect"> <h5 class="fa noselect">

View File

@@ -15,13 +15,14 @@
<?php <?php
$partial = new Partial('menu'); $partial = new Partial('menu');
$partial->prepare('item', 'rooms'); $partial->prepare('item', 'rooms');
$partial->prepare('lang',$LANG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('debugMod',$DEBUGMOD);
$partial->render(); $partial->render();
?> ?>
</div> </div>
<div class="col-md-9 main-body"> <div class="col-md-9 main-body">
<div class="frame"> <div class="frame">
<?php foreach ($ROOMS as $roomId => $room) { ?> <?php foreach ($ROOMS as $roomId => $room) { ?>
@@ -29,7 +30,7 @@
<div class=""> <div class="">
<h1><?php echo $room['name']; ?></h1> <h1><?php echo $room['name']; ?></h1>
<?php foreach ($room['reading'] as $key => $value) { ?> <?php foreach ($room['reading'] as $key => $value) { ?>
<?php echo $LANG[$key] .": ". $value; ?></br> <?php echo $LANGMNG->get($key) .": ". $value; ?></br>
<?php } ?> <?php } ?>
<?php if (DEBUGMOD == 1) { ?> <?php if (DEBUGMOD == 1) { ?>
<pre> <pre>
@@ -72,26 +73,26 @@
flex: 0 0 100%; flex: 0 0 100%;
height: 100%; height: 100%;
} }
.frame { .frame {
overflow-x: auto; overflow-x: auto;
width: 100%; width: 100%;
display: flex; display: flex;
height: 100%; height: 100%;
} }
body,html{ body,html{
height: 100%; height: 100%;
} }
.frame .single-frame:nth-child(even) { .frame .single-frame:nth-child(even) {
background: red; background: red;
} }
.frame .single-frame:nth-child(odd) { .frame .single-frame:nth-child(odd) {
background: green; background: green;
} }
</style> </style>
</div> </div>
</div> </div>
@@ -104,27 +105,27 @@
var id; var id;
var current_element var current_element
var elementWidth = $('.frame').width(); var elementWidth = $('.frame').width();
$('.frame').scroll(function(){ $('.frame').scroll(function(){
//console.log('SCROLLING!'); //console.log('SCROLLING!');
//console.log('scrool'+$('.single-frame').scrollLeft()); //console.log('scrool'+$('.single-frame').scrollLeft());
var element_width = $('.single-frame').width(); var element_width = $('.single-frame').width();
var offset = $('.single-frame').offset(); var offset = $('.single-frame').offset();
var positive = Math.abs(offset.left) var positive = Math.abs(offset.left)
var divided = positive / element_width; var divided = positive / element_width;
var round = Math.round(divided); var round = Math.round(divided);
current_element = $('.frame').children().eq(round); current_element = $('.frame').children().eq(round);
id = current_element.attr('id'); id = current_element.attr('id');
if (prev_id != id){ if (prev_id != id){
prev_id = id; prev_id = id;
console.log(prev_id); console.log(prev_id);
} }
var scrollTo = $('#'+id).offset().left; var scrollTo = $('#'+id).offset().left;
console.log('s-f: '+ scrollTo) console.log('s-f: '+ scrollTo)
}); });
$('.frame').on('touchend', function(){ // listen to mouse up $('.frame').on('touchend', function(){ // listen to mouse up
console.log('STOPPED SCROLLING!'); console.log('STOPPED SCROLLING!');
@@ -135,19 +136,19 @@
if(a[index].id == id){ if(a[index].id == id){
$('.frame').animate({ $('.frame').animate({
scrollLeft: (index * elementWidth) scrollLeft: (index * elementWidth)
}); });
$('.frame').animate({ $('.frame').animate({
scrollLeft: (index * elementWidth) scrollLeft: (index * elementWidth)
}); });
} }
console.log(a[index]); console.log(a[index]);
} }
if (scrollTo > 160) { if (scrollTo > 160) {
console.log($('#'+id).left) console.log($('#'+id).left)
} }
}); });
</script> </script>
</body> </body>
</html> </html>

View File

@@ -16,51 +16,52 @@
$partial = new Partial('menu'); $partial = new Partial('menu');
$partial->prepare('item', 'scene'); $partial->prepare('item', 'scene');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('debugMod',$DEBUGMOD);
$partial->render(); $partial->render();
?> ?>
</div> </div>
<div class="col-md-9 main-body"> <div class="col-md-9 main-body">
<a class="button is-primary m-1" onClick="$('#modal').removeClass('modal-container-hiden').show();"><?php $LANGMNG->echo('t_createScene');?></a> <a class="button is-primary m-1" onClick="$('#modal').removeClass('modal-container-hiden').show();"><?php $LANGMNG->echo('t_createScene');?></a>
<div class="row no-gutters"> <div class="row no-gutters">
<?php foreach ($SCENES as $sceneId => $sceneData) { <?php foreach ($SCENES as $sceneId => $sceneData) {
//BUTTON //BUTTON
$partialScenButton = new Partial('sceneButton'); $partialScenButton = new Partial('sceneButton');
$partialScenButton->prepare('langMng', $LANGMNG); $partialScenButton->prepare('langMng', $LANGMNG);
$partialScenButton->prepare('sceneId', $sceneId); $partialScenButton->prepare('sceneId', $sceneId);
$partialScenButton->prepare('sceneData', $sceneData); $partialScenButton->prepare('sceneData', $sceneData);
$partialScenButton->render(); $partialScenButton->render();
// Edit // Edit
$partialSceneEdit = new Partial('sceneEdit'); $partialSceneEdit = new Partial('sceneEdit');
$partialSceneEdit->prepare('langMng',$LANGMNG); $partialSceneEdit->prepare('langMng',$LANGMNG);
$partialSceneEdit->prepare('sceneId',$sceneId); $partialSceneEdit->prepare('sceneId',$sceneId);
$partialSceneEdit->prepare('scene',$sceneData); $partialSceneEdit->prepare('scene',$sceneData);
$partialSceneEdit->render(); $partialSceneEdit->render();
?> ?>
<?php } ?> <?php } ?>
</div> </div>
</div> </div>
</div> </div>
<?php if (isset($_POST['submit'])) { <?php if (isset($_POST['submit'])) {
$partial = new Partial('sceneCreateFinal'); $partial = new Partial('sceneCreateFinal');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('setStateFormDevices',$SETSTATEFORMDEVICES ); $partial->prepare('setStateFormDevices',$SETSTATEFORMDEVICES );
$partial->prepare('sceneIcon',$SCENEICON ); $partial->prepare('sceneIcon',$SCENEICON );
$partial->prepare('SceneName',$SCENENAME ); $partial->prepare('SceneName',$SCENENAME );
$partial->render(); $partial->render();
} else { } else {
$partial = new Partial('sceneCreate'); $partial = new Partial('sceneCreate');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('subDevices',$SUBDEVICES); $partial->prepare('subDevices',$SUBDEVICES);
$partial->render(); $partial->render();
} }
$partial = new Partial('footer'); $partial = new Partial('footer');
$partial->render(); $partial->render();
?> ?>
</body> </body>
</html> </html>

View File

@@ -16,12 +16,14 @@
$partial = new Partial('menu'); $partial = new Partial('menu');
$partial->prepare('item', 'setting'); $partial->prepare('item', 'setting');
$partial->prepare('langMng',$LANGMNG); $partial->prepare('langMng',$LANGMNG);
$partial->prepare('debugMod',$DEBUGMOD);
$partial->render(); $partial->render();
?> ?>
</div> </div>
<div class="col-md-9 main-body"> <div class="col-md-9 main-body">
<div class="col-12 col-sm-9 mx-auto mt-4"> <div class="col-12 col-sm-9 mx-auto mt-4">
<h4 class="mb-4"> <h4 class="mb-4">
<?php $LANGMNG->echo('t_pageAfterLogIn') ?> <?php $LANGMNG->echo('t_pageAfterLogIn') ?>
</h4> </h4>
<form method="post" enctype="multipart/form-data"> <form method="post" enctype="multipart/form-data">
@@ -38,6 +40,19 @@
</form> </form>
<div class="col-12 col-sm-9 mx-auto mt-4"> <div class="col-12 col-sm-9 mx-auto mt-4">
<h4 class="mb-4"><?php $LANGMNG->echo('t_profile') ?></h4> <h4 class="mb-4"><?php $LANGMNG->echo('t_profile') ?></h4>
<div class="field">
<div class="label"><?php $LANGMNG->echo('l_userAvatar') ?>:</div>
<img src="<?php echo $USERAVATARURL; ?>" />
<div class="label">* providet by Gavatar</div>
</div>
<div class="field">
<div class="label"><?php $LANGMNG->echo('l_userName') ?>:</div>
<input class="input" value="<?php echo $USERNAME; ?>" disabled>
</div>
<div class="field">
<div class="label"><?php $LANGMNG->echo('l_userEmail') ?>:</div>
<input class="input" value="<?php echo $USEREMAIL; ?>" disabled>
</div>
<div class="field"> <div class="field">
<a href="logout" class="button is-primary"><?php $LANGMNG->echo('b_logOut') ?></a> <a href="logout" class="button is-primary"><?php $LANGMNG->echo('b_logOut') ?></a>
</div> </div>
@@ -100,6 +115,7 @@
<table class="table is-fluid"> <table class="table is-fluid">
<thead> <thead>
<tr> <tr>
<th><?php $LANGMNG->echo('t_avatar');?></th>
<th><?php $LANGMNG->echo('t_userName');?></th> <th><?php $LANGMNG->echo('t_userName');?></th>
<th><?php $LANGMNG->echo('t_ota');?></th> <th><?php $LANGMNG->echo('t_ota');?></th>
<th><?php $LANGMNG->echo('t_action');?></th> <th><?php $LANGMNG->echo('t_action');?></th>
@@ -108,6 +124,7 @@
<tbody> <tbody>
<?php foreach ($USERS as $key => $user) { ?> <?php foreach ($USERS as $key => $user) { ?>
<tr> <tr>
<td><img src="<?php echo $user['gavatar_url']; ?>" /></td>
<td><?php echo $user['username']; ?></td> <td><?php echo $user['username']; ?></td>
<td><?php echo ($user['ota'] ? '<span class="fa">&#xf00c;</span>' : ''); ?></td> <td><?php echo ($user['ota'] ? '<span class="fa">&#xf00c;</span>' : ''); ?></td>
<td><button name="deleteUser" type="button" class="button is-danger fa">&#xf1f8;</button></td> <td><button name="deleteUser" type="button" class="button is-danger fa">&#xf1f8;</button></td>
@@ -121,17 +138,57 @@
<form method="post"> <form method="post">
<div class="field"> <div class="field">
<div class="label"><?php $LANGMNG->echo('l_userName') ?>:</div> <div class="label"><?php $LANGMNG->echo('l_userName') ?>:</div>
<input type="text" class="input" name="userName" value="" data-cip-id="cIPJQ342845639"> <input type="text" class="input" name="userName" value="">
</div> </div>
<div class="field"> <div class="field">
<div class="label"><?php $LANGMNG->echo('l_password') ?>:</div> <div class="label"><?php $LANGMNG->echo('l_password') ?>:</div>
<input type="password" class="input" name="userPassword" value="" data-cip-id="cIPJQ342845639"> <input type="password" class="input" name="userPassword" value="">
</div> </div>
<div class="field"> <div class="field">
<input type="submit" name="submitCreateUser" class="button" value="Uložit"> <input type="submit" name="submitCreateUser" class="button" value="Uložit">
</div> </div>
</form> </form>
</div> </div>
<!--Room Managment-->
<div class="col-12 col-sm-9 mx-auto mt-4">
<h4 class="mb-4"><?php $LANGMNG->echo('t_listRooms') ?></h4>
<table class="table is-fluid">
<thead>
<tr>
<th><?php $LANGMNG->echo('t_roomName');?></th>
<th><?php $LANGMNG->echo('t_action');?></th>
</tr>
</thead>
<tbody>
<?php foreach ($ROOMS as $key => $room) { ?>
<tr>
<td><?php echo $room['name']; ?></td>
<td>
<button name="deleteRoom" type="button" class="button is-danger fa">&#xf1f8;</button>
<button name="defaultRoom" type="button" class="button fa" <?php echo ($room['default'] ? 'disabled' : ''); ?>>&#xf140;</button>
</td>
</tr>
<?php } ?>
</tbody>
</table>
</div>
<!--Room Creation-->
<div class="col-12 col-sm-9 mx-auto mt-4">
<h4 class="mb-4"><?php $LANGMNG->echo('t_createRoom') ?></h4>
<form method="post">
<div class="field">
<div class="label"><?php $LANGMNG->echo('l_roomName') ?>:</div>
<input type="text" class="input" name="roomName" value="">
</div>
<div class="field">
<input type="submit" name="submitCreateUser" class="button" value="<?php $LANGMNG->echo('b_create') ?>">
</div>
</form>
</div>
</div> </div>

0
app/updater/.gitkeep Normal file
View File

View File

@@ -129,7 +129,7 @@ class Ajax extends Template
$notificationData = [ $notificationData = [
'title' => 'Alert', 'title' => 'Alert',
'body' => 'test notification', 'body' => 'test notification',
'icon' => '', 'icon' => BASEDIR . '/app/templates/images/icon-192x192.png',
]; ];
$notificationMng = new NotificationManager; $notificationMng = new NotificationManager;
$subscribers = $notificationMng::getSubscription(); $subscribers = $notificationMng::getSubscription();
@@ -145,6 +145,77 @@ class Ajax extends Template
echo 'no action detected'; echo 'no action detected';
break; break;
} }
} else if (
isset($_POST['action']) &&
$_POST['action'] != ''
) {
$updateData = [];
$allDevicesData = DeviceManager::getAllDevices();
foreach ($allDevicesData as $deviceKey => $deviceValue) {
$allSubDevices = SubDeviceManager::getAllSubDevices($deviceValue['device_id']);
foreach ($allSubDevices as $key => $subDevicesData) {
$lastRecord = RecordManager::getLastRecord($subDevicesData['subdevice_id']);
$parsedValue = $lastRecord['value'] . $subDevicesData['unit'];
//TODO: udělat parser a ten použít jak v houmu tak zde
switch ($subDevicesData['type']) {
case 'on/off':
$replacementTrue = 'On';
$replacementFalse = 'Off';
$operator = '==';
$breakValue = 1;
break;
case 'door':
$replacementTrue = 'Closed';
$replacementFalse = 'Open';
$operator = '==';
$breakValue = 1;
break;
case 'light':
$replacementTrue = 'Light';
$replacementFalse = 'Dark';
$operator = '==';
$breakValue = 1;
if ($lastRecord['value'] != 1 && $lastRecord['value'] != 0) { //Digital Light Senzor
$operator = '<';
$breakValue = 810;
}
break;
case 'water':
$replacementTrue = 'Wet';
$replacementFalse = 'Dry';
$operator = '==';
$breakValue = 1;
break;
default:
$replacementTrue = '';
$replacementFalse = '';
break;
}
if ($replacementTrue != '' && $replacementFalse != '') {
//parsing last values
$parsedValue = $replacementFalse;
if (Utilities::checkOperator($lastRecord['value'], $operator, $breakValue)) {
$parsedValue = $replacementTrue;
}
}
$updateData[$subDevicesData['subdevice_id']] = [
'time' => $lastRecord['time'],
'value' => $parsedValue,
];
}
}
//TODO: PRO JS VRACET DATA
echo json_encode($updateData, JSON_PRETTY_PRINT);
} }
} }
} }

View File

@@ -27,12 +27,19 @@ class Automation extends Template
'state' => $subDeviceState, 'state' => $subDeviceState,
]; ];
} }
//TODO: Transaltion add
$executionTime = 'never';
if ($automationData['execution_time'] != '0000-00-00 00:00:00') {
$executionTime = date(DATEFORMAT,strtotime($automationData['execution_time']));
}
$automations[$automationData['automation_id']] = [ $automations[$automationData['automation_id']] = [
'name' => $automationData['name'], 'name' => $automationData['name'],
'owner_name' => $userManager->getUserId($automationData['owner_id'])['username'],
'onDays' => json_decode($automationData['on_days']), 'onDays' => json_decode($automationData['on_days']),
'ifSomething' => $automationData['if_something'], 'ifSomething' => $automationData['if_something'],
'doSomething' => $doSomething, 'doSomething' => $doSomething,
'active' => $automationData['active'], 'active' => $automationData['active'],
'execution_time' => $executionTime,
]; ];
} }
@@ -52,8 +59,11 @@ class Automation extends Template
$template = new Template('automation'); $template = new Template('automation');
$template->prepare('baseDir', BASEDIR); $template->prepare('baseDir', BASEDIR);
$template->prepare('debugMod', DEBUGMOD);
$template->prepare('title', 'Automation'); $template->prepare('title', 'Automation');
$template->prepare('langMng', $langMng); $template->prepare('langMng', $langMng);
$template->prepare('userManager', $userManager);
$template->prepare('automations', $automations); $template->prepare('automations', $automations);
$template->prepare('subDevices', $approvedSubDevices); $template->prepare('subDevices', $approvedSubDevices);

View File

@@ -81,6 +81,7 @@ class Dashboard extends Template
} }
$template->prepare('baseDir', BASEDIR); $template->prepare('baseDir', BASEDIR);
$template->prepare('debugMod', DEBUGMOD);
$template->prepare('title', 'Nástěnka'); $template->prepare('title', 'Nástěnka');
$template->prepare('langMng', $langMng); $template->prepare('langMng', $langMng);
$template->prepare('dashboard', $dashboard); $template->prepare('dashboard', $dashboard);

View File

@@ -77,8 +77,8 @@ class Home extends Template
$replacementFalse = 'Dark'; $replacementFalse = 'Dark';
$operator = '=='; $operator = '==';
$breakValue = 1; $breakValue = 1;
if ($lastValue != 1 || $lastValue != 0) { //Digital Light Senzor if ($lastValue != 1 && $lastValue != 0) { //Digital Light Senzor
$operator = '<='; $operator = '<';
$breakValue = 810; $breakValue = 810;
} }
break; break;
@@ -108,7 +108,7 @@ class Home extends Template
//parsing last events values //parsing last events values
foreach ($events as $key => $value) { foreach ($events as $key => $value) {
$events[$key]['value'] = $replacementFalse; $events[$key]['value'] = $replacementFalse;
if (Utilities::checkOperator($lastValue, $operator, $breakValue)) { if (Utilities::checkOperator($value['value'], $operator, $breakValue)) {
$events[$key]['value'] = $replacementTrue; $events[$key]['value'] = $replacementTrue;
} }
} }
@@ -122,7 +122,11 @@ class Home extends Template
$minutes = $interval->format('%i'); $minutes = $interval->format('%i');
$lastSeen = ($hours * 60 + $minutes); $lastSeen = ($hours * 60 + $minutes);
if ($lastSeen < $deviceData['sleep_time'] || $subDeviceData['type'] == "on/off") { if (
$lastSeen < $deviceData['sleep_time'] ||
$subDeviceData['type'] == "on/off" ||
$subDeviceData['type'] == "door"
) {
$connectionError = false; $connectionError = false;
} }
} }
@@ -156,6 +160,11 @@ class Home extends Template
'icon' => $deviceData['icon'], 'icon' => $deviceData['icon'],
'room' => $deviceData['room_id'], 'room' => $deviceData['room_id'],
'token' => $deviceData['token'], 'token' => $deviceData['token'],
'type' => $deviceData['type'],
'mac' => $deviceData['mac'],
'ip' => $deviceData['ip_address'],
'subnet' => $deviceData['subnet'],
'gateway' => $deviceData['gateway'],
'sleepTime' => $deviceData['sleep_time'], 'sleepTime' => $deviceData['sleep_time'],
'approved' => $deviceData['approved'], 'approved' => $deviceData['approved'],
'permission' => $permissionArray, 'permission' => $permissionArray,
@@ -173,6 +182,7 @@ class Home extends Template
$rooms = RoomManager::getAllRooms(); $rooms = RoomManager::getAllRooms();
$template->prepare('baseDir', BASEDIR); $template->prepare('baseDir', BASEDIR);
$template->prepare('debugMod', DEBUGMOD);
$template->prepare('title', 'Home'); $template->prepare('title', 'Home');
$template->prepare('rooms', $rooms); $template->prepare('rooms', $rooms);
$template->prepare('langMng', $langMng); $template->prepare('langMng', $langMng);

View File

@@ -26,6 +26,8 @@ class Log extends Template
} }
$template->prepare('baseDir', BASEDIR); $template->prepare('baseDir', BASEDIR);
$template->prepare('debugMod', DEBUGMOD);
$template->prepare('logToLiveTime', LOGTIMOUT);
$template->prepare('title', 'Logy'); $template->prepare('title', 'Logy');
$template->prepare('logsFiles', $result); $template->prepare('logsFiles', $result);
$template->prepare('langMng', $langMng); $template->prepare('langMng', $langMng);

View File

@@ -15,6 +15,8 @@ class Login extends Template
$template->prepare('title', 'Home'); $template->prepare('title', 'Home');
$template->prepare('lang', $lang); $template->prepare('lang', $lang);
$template->render(); $template->render();
} }
} }

View File

@@ -6,7 +6,7 @@ class Rooms extends Template
function __construct() function __construct()
{ {
global $userManager; global $userManager;
global $lang; global $langMng;
if (!$userManager->isLogin()){ if (!$userManager->isLogin()){
header('Location: ' . BASEDIR . 'login'); header('Location: ' . BASEDIR . 'login');
@@ -15,8 +15,9 @@ class Rooms extends Template
$template = new Template('rooms'); $template = new Template('rooms');
$template->prepare('baseDir', BASEDIR); $template->prepare('baseDir', BASEDIR);
$template->prepare('debugMod', DEBUGMOD);
$template->prepare('title', 'Rooms'); $template->prepare('title', 'Rooms');
$template->prepare('lang', $lang); $template->prepare('langMng', $langMng);
$roomsItems = []; $roomsItems = [];
$roomsData = RoomManager::getAllRooms(); $roomsData = RoomManager::getAllRooms();

View File

@@ -12,6 +12,7 @@ class Scene extends Template
$template = new Template('scene'); $template = new Template('scene');
$template->prepare('baseDir', BASEDIR); $template->prepare('baseDir', BASEDIR);
$template->prepare('debugMod', DEBUGMOD);
$template->prepare('title', 'Scény'); $template->prepare('title', 'Scény');
$template->prepare('langMng', $langMng); $template->prepare('langMng', $langMng);

View File

@@ -24,13 +24,21 @@ class Setting extends Template
$template = new Template('setting'); $template = new Template('setting');
$template->prepare('baseDir', BASEDIR); $template->prepare('baseDir', BASEDIR);
$template->prepare('debugMod', DEBUGMOD);
$template->prepare('title', 'Automation'); $template->prepare('title', 'Automation');
$template->prepare('langMng', $langMng); $template->prepare('langMng', $langMng);
$template->prepare('automations', $automations); $template->prepare('automations', $automations);
$users = $userManager->getUsers(); $users = $userManager->getUsers();
foreach ($users as $key => $value) {
$users[$key]['gavatar_url'] = $userManager->getAvatarUrl($value['user_id']);
}
$template->prepare('users', $users); $template->prepare('users', $users);
$template->prepare('userName', $userManager->getUserData('username'));
$template->prepare('userEmail', $userManager->getUserData('email'));
$template->prepare('userAvatarUrl', $userManager->getAvatarUrl());
if ($userManager->getUserData('ota') == ''){ if ($userManager->getUserData('ota') == ''){
$ga = new PHPGangsta_GoogleAuthenticator(); $ga = new PHPGangsta_GoogleAuthenticator();
$otaSecret = $ga->createSecret(); $otaSecret = $ga->createSecret();
@@ -45,6 +53,9 @@ class Setting extends Template
// echo "Checking Code '$oneCode' and Secret '$otaSecret':\n"; // echo "Checking Code '$oneCode' and Secret '$otaSecret':\n";
} }
$rooms = RoomManager::getAllRooms();
$template->prepare('rooms', $rooms);
$template->render(); $template->render();
} }

34
make.sh Normal file
View File

@@ -0,0 +1,34 @@
#! /bin/sh
apt install dialog;
#dialog --stdout --title "Smart-Home" \
#--backtitle "Select update chanel :)" \
#--yesno "DEV: Experimental Version, STABLE: Stable version" 7 60
#dialog_status=$?
# Do something
dialog --menu "The best tortilla is:" 0 0 0 1 "with onions" 2 "without onion" 3 "with piminetos"
echo "answer $?";
#if [ "$dialo_status" -eq 'DEV' ]; then
# The previous dialog was answered Yes
#git checkout dev;
#else
# The previous dialog was answered No or interrupted with <C-c>
#git checkout master;
#fi
#clear;
#git reset --hard HEAD
#git pull
#rm ./.gitignore
#rm ./.ftpignore
#rm ./.todo
#rm ./LICENCE
#rm ./README.md
#rm -rf ./_FIRMWARE/*
#rm -rf ./_INSTALATION/*
#rm -rf ./_README_IMG/*
echo "Done";

180
old.home Normal file
View File

@@ -0,0 +1,180 @@
<!-- <?php
//
// class Home extends Template
// {
// function __construct()
// {
// global $userManager;
// global $lang;
//
// if (!$userManager->isLogin()){
// header('Location: ./login');
// }
//
// $template = new Template('home');
//
// //users instantialize
// $users = UserManager::getUsers();
// $template->prepare('users', $users);
//
// //Users at home Info
// $usersAtHome = '';
// $i = 0;
// foreach ($users as $user) {
// $i++;
// if ($user['at_home'] == 'true') {
// $usersAtHome .= $user['username'];
// if ($usersAtHome != "" && isset($users[$i + 1])){
// $usersAtHome .= ', ';
// }
// }
// }
// $template->prepare('usersAtHome', $usersAtHome);
//
// $roomsItems = [];
// $roomsData = RoomManager::getAllRooms();
// foreach ($roomsData as $roomKey => $roomsData) {
// $devices = [];
// $devicesData = DeviceManager::getAllDevicesInRoom($roomsData['room_id']);
// foreach ($devicesData as $deviceKey => $deviceData) {
// $subDevices = [];
// $subDevicesData = SubDeviceManager::getAllSubDevices($deviceData['device_id']);
// foreach ($subDevicesData as $subDeviceKey => $subDeviceData) {
//
// $events = RecordManager::getLastRecord($subDeviceData['subdevice_id'], 5);
//
// $connectionError = false;
// $parsedValue = "";
// $niceTime = "";
//
// if (sizeof($events) > 1) {
//
// //TODO: skontrolovat zdali se jedná o poslední (opravdu nejaktuálnější) záznam
// $lastRecord = $events[0];
//
// $parsedValue = round($lastRecord['value']);
//
// /*Value Parsing*/
// if ($subDeviceData['type'] == "on/off") {
// $parsedValue = ($parsedValue == 1 ? 'ON' : 'OFF');
// }
//
// if ($subDeviceData['type'] == "door") {
// $replacementTrue = 'Closed';
// $replacementFalse = 'Opened';
// foreach ($events as $key => $value) {
// $events[$key]['value'] = ($value['value'] == 1 ? $replacementTrue : $replacementFalse);
// }
// $parsedValue = ($parsedValue == 1 ? $replacementTrue : $replacementFalse);
// }
//
// if ($subDeviceData['type'] == "light") {
// $replacementTrue = 'Light';
// $replacementFalse = 'Dark';
// foreach ($events as $key => $value) {
// if ($parsedValue != 1){
// //Analog Reading
// $events[$key]['value'] = ($value['value'] <= 810 ? $replacementTrue : $replacementFalse);
// } else {
// //Digital Reading
// $events[$key]['value'] = ($value['value'] == 0 ? $replacementTrue : $replacementFalse);
// }
// }
// if ($parsedValue != 1){
// //Analog Reading
// $parsedValue = ($parsedValue <= 810 ? $replacementTrue : $replacementFalse);
// } else {
// //Digital Reading
// $parsedValue = ($parsedValue == 0 ? $replacementTrue : $replacementFalse);
// }
// }
//
// $date2 = new DateTime($lastRecord['time']);
//
// $niceTime = $this->ago($date2);
//
//
// $startDate = date_create($lastRecord['time']);
// $interval = $startDate->diff(new DateTime());
// $hours = $interval->format('%h');
// $minutes = $interval->format('%i');
// $lastSeen = ($hours * 60 + $minutes);
//
// if ($lastSeen > $deviceData['sleep_time'] && $subDeviceData['type'] != "on/off") {
// $connectionError = true;
// }
// } else {
// $connectionError = true;
// }
//
// $subDevices[$subDeviceData['subdevice_id']] = [
// 'events'=> $events,
// 'type' => $subDeviceData['type'],
// 'unit' => $subDeviceData['unit'],
// 'comError' => $connectionError,
// 'lastRecort' => [
// 'value' => (empty($parsedValue) ? 0 : $parsedValue),
// 'time' => (empty($lastRecord['time']) ? "00:00" : $lastRecord['time']),
// 'niceTime' => (empty($niceTime) ? "00:00" : $niceTime),
// ],
// ];
// }
//
// $permissionArray = json_decode($deviceData['permission']);
//
// $userIsDeviceAdmin = false;
// if($permissionArray[1] == 3) {
// $userIsDeviceAdmin = true;
// } else if ($permissionArray[0] == 3) {
// if ( $deviceData['owner'] == $userManager->getUserData('user_id')) {
// $userIsDeviceAdmin = true;
// }
// }
//
// $devices[$deviceData['device_id']] = [
// 'name' => $deviceData['name'],
// 'icon' => $deviceData['icon'],
// 'room' => $deviceData['room_id'],
// 'token' => $deviceData['token'],
// 'sleepTime' => $deviceData['sleep_time'],
// 'approved' => $deviceData['approved'],
// 'permission' => $permissionArray,
// 'owner' => $deviceData['owner'],
// 'userIsAdmin' => $userIsDeviceAdmin,
// 'subDevices' => $subDevices,
// ];
// }
// $roomsItems[$roomsData['room_id']] = [
// 'name' => $roomsData['name'],
// 'deviceCount' => $roomsData['device_count'],
// 'devices' => $devices,
// ];
// }
//
// $rooms = RoomManager::getAllRooms();
// $template->prepare('rooms', $rooms);
// $template->prepare('title', 'Home');
// $template->prepare('lang', $lang);
// $template->prepare('data', $roomsItems);
//
// $template->render();
//
// }
//
// function ago( $datetime )
// {
// $interval = date_create('now')->diff( $datetime );
// $suffix = ( $interval->invert ? ' ago' : '' );
// if ( $v = $interval->y >= 1 ) return $this->pluralize( $interval->m, 'month' ) . $suffix;
// if ( $v = $interval->d >= 1 ) return $this->pluralize( $interval->d, 'day' ) . $suffix;
// if ( $v = $interval->h >= 1 ) return $this->pluralize( $interval->h, 'hour' ) . $suffix;
// if ( $v = $interval->i >= 1 ) return $this->pluralize( $interval->i, 'minute' ) . $suffix;
// return $this->pluralize( $interval->s, 'second' ) . $suffix;
// }
//
// function pluralize( $count, $text )
// {
// return $count . ( ( $count == 1 ) ? ( " $text" ) : ( " ${text}s" ) );
// }
// }

View File

@@ -1,6 +1,7 @@
<pre> <pre>
<?php <?php
var_dump($_POST); var_dump($_POST);
var_dump(file_exists("./app/updater/" . "3C71BF22FDCF" . ".bin"));
?> ?>
</pre> </pre>

91
update.php Normal file
View File

@@ -0,0 +1,91 @@
<?PHP
/** Includes **/
include_once('./config.php');
//Autoloader
$files = scandir('./app/class/');
$files = array_diff($files, array(
'.',
'..',
'app',
'ChartJS.php',
'ChartJS_Line.php',
'ChartManager.php',
'DashboardManager.php',
'Partial.php',
'Form.php',
'Route.php',
'Template.php',
'Ajax.php',
));
foreach($files as $file) {
include './app/class/'. $file;
}
//DB Conector
Db::connect (DBHOST, DBUSER, DBPASS, DBNAME);
$logManager = new LogManager();
header('Content-type: text/plain; charset=utf8', true);
//Filtrování IP adress
if (DEBUGMOD != 1) {
if (!in_array($_SERVER['REMOTE_ADDR'], HOMEIP)) {
echo json_encode(array(
'state' => 'unsuccess',
'errorMSG' => "Using API from your IP insnt alowed!",
));
header($_SERVER["SERVER_PROTOCOL"]." 401 Unauthorized");
$logManager->write("[Updater] acces denied from " . $_SERVER['REMOTE_ADDR'], LogRecordType::WARNING);
exit();
}
}
function sendFile($path)
{
header($_SERVER["SERVER_PROTOCOL"] . ' 200 OK', true, 200);
header('Content-Type: application/octet-stream', true);
header('Content-Disposition: attachment; filename=' . basename($path));
header('Content-Length: ' . filesize($path), true);
header('x-MD5: ' . md5_file($path), true);
readfile($path);
}
$macAddress = $_SERVER['HTTP_X_ESP8266_STA_MAC'];
$localBinary = "./app/updater/" . str_replace(':', '', $macAddress) . ".bin";
$logManager->write("[Updater] url: " . $localBinary, LogRecordType::INFO);
$logManager->write("[Updater] version: " . $_SERVER['HTTP_X_ESP8266_SKETCH_MD5'], LogRecordType::INFO);
if (file_exists($localBinary)) {
$logManager->write("[Updater] version PHP: \n" . md5_file($localBinary), LogRecordType::INFO);
if ($_SERVER['HTTP_X_ESP8266_SKETCH_MD5'] != md5_file($localBinary)) {
sendFile($localBinary);
//get device data
$device = DeviceManager::getDeviceByMac($macAddress);
$deviceName = $device['name'];
$deviceId = $device['device_id'];
//logfile write
$logManager->write("[Device] device_ID " . $deviceId . " was just updated to new version", LogRecordType::WARNING);
$logManager->write("[Device] version hash: \n" . md5_file($localBinary), LogRecordType::INFO);
//notification
$notificationMng = new NotificationManager;
$notificationData = [
'title' => 'Info',
'body' => $deviceName.' was just updated to new version',
'icon' => BASEDIR . '/app/templates/images/icon-192x192.png',
];
if ($notificationData != []) {
$subscribers = $notificationMng->getSubscription();
foreach ($subscribers as $key => $subscriber) {
$logManager->write("[NOTIFICATION] SENDING TO " . $subscriber['id'] . " ", LogRecordType::INFO);
$answer = $notificationMng->sendSimpleNotification(SERVERKEY, $subscriber['token'], $notificationData);
}
}
} else {
header($_SERVER["SERVER_PROTOCOL"].' 304 Not Modified', true, 304);
}
} else {
header($_SERVER["SERVER_PROTOCOL"]." 404 Not Found");
}
die();