mirror of
https://github.com/IoTManagerProject/IoTManager.git
synced 2026-03-26 22:22:16 +03:00
добавление логирования
This commit is contained in:
@@ -35,6 +35,8 @@
|
||||
#define USE_LITTLEFS false
|
||||
#endif
|
||||
|
||||
#define START_DATETIME 1640995200 // 01.01.2022 00:00:00 константа для сокрацения unix time
|
||||
|
||||
#define MIN_DATETIME 1575158400
|
||||
#define LEAP_YEAR(Y) (((1970 + Y) > 0) && !((1970 + Y) % 4) && (((1970 + Y) % 100) || !((1970 + Y) % 400)))
|
||||
|
||||
|
||||
@@ -130,6 +130,8 @@ struct Time_t {
|
||||
};
|
||||
|
||||
extern unsigned long unixTime;
|
||||
extern unsigned long unixTimeShort;
|
||||
|
||||
extern bool isTimeSynch;
|
||||
extern Time_t _time_local;
|
||||
extern Time_t _time_utc;
|
||||
|
||||
@@ -31,6 +31,9 @@ void publishState();
|
||||
void mqttCallback(char* topic, uint8_t* payload, size_t length);
|
||||
void handleMqttStatus(bool send);
|
||||
void handleMqttStatus(bool send, int state);
|
||||
void sendAllFilesToMQTT();
|
||||
void sendLogData(String file, String topic);
|
||||
|
||||
const String getStateStr(int e);
|
||||
|
||||
void mqttUptimeCalc();
|
||||
|
||||
@@ -10,4 +10,6 @@ extern const String addFileLn(const String& filename, const String& str);
|
||||
extern const String readFile(const String& filename, size_t max_size);
|
||||
extern const String filepath(const String& filename);
|
||||
extern bool cutFile(const String& src, const String& dst);
|
||||
extern size_t countLines(const String filename);
|
||||
void removeFile(const String& filename);
|
||||
extern void onFlashWrite();
|
||||
@@ -66,6 +66,8 @@ String mqttRootDevice = "";
|
||||
|
||||
// Time
|
||||
unsigned long unixTime = 0;
|
||||
unsigned long unixTimeShort = 0;
|
||||
|
||||
bool isTimeSynch = false;
|
||||
Time_t _time_local;
|
||||
Time_t _time_utc;
|
||||
|
||||
@@ -133,6 +133,9 @@ void mqttCallback(char* topic, uint8_t* payload, size_t length) {
|
||||
SerialPrint("i", F("MQTT"), F("Full update"));
|
||||
publishWidgets();
|
||||
publishState();
|
||||
|
||||
sendAllFilesToMQTT();
|
||||
|
||||
#ifdef GATE_MODE
|
||||
publishTimes();
|
||||
#endif
|
||||
@@ -308,6 +311,52 @@ void handleMqttStatus(bool send, int state) {
|
||||
if (!send) standWebSocket.broadcastTXT(errorsHeapJson);
|
||||
}
|
||||
|
||||
// log-20384820.txt
|
||||
void sendAllFilesToMQTT() {
|
||||
String directory = "logs";
|
||||
SerialPrint("I", "Loging", "in directory '" + directory + "' files:");
|
||||
auto dir = FileFS.openDir(directory);
|
||||
while (dir.next()) {
|
||||
String fname = dir.fileName();
|
||||
String id = selectToMarker(fname, "-");
|
||||
SerialPrint("I", "Loging", fname);
|
||||
sendLogData("/logs/" + fname, id);
|
||||
}
|
||||
}
|
||||
|
||||
void sendLogData(String file, String topic) {
|
||||
File configFile = FileFS.open(file, "r");
|
||||
if (!configFile) {
|
||||
return;
|
||||
}
|
||||
configFile.seek(0, SeekSet);
|
||||
int i = 0;
|
||||
String buf = "{}";
|
||||
String json_array;
|
||||
String unix_time;
|
||||
String value;
|
||||
unsigned int psn;
|
||||
unsigned int sz = configFile.size();
|
||||
do {
|
||||
i++;
|
||||
psn = configFile.position();
|
||||
String line = configFile.readStringUntil('\n');
|
||||
unix_time = selectToMarker(line, " ");
|
||||
jsonWriteInt(buf, "x", unix_time.toInt() + START_DATETIME);
|
||||
value = deleteBeforeDelimiter(line, " ");
|
||||
jsonWriteFloat(buf, "y1", value.toFloat());
|
||||
if (unix_time != "" || value != "") {
|
||||
json_array += buf + ",";
|
||||
}
|
||||
} while (psn < sz);
|
||||
|
||||
configFile.close();
|
||||
|
||||
json_array = "{\"status\":[" + json_array + "]}";
|
||||
json_array.replace("},]}", "}]}");
|
||||
publishChart(topic, json_array);
|
||||
}
|
||||
|
||||
const String getStateStr(int e) {
|
||||
switch (e) {
|
||||
case -4: //Нет ответа от сервера
|
||||
|
||||
@@ -9,6 +9,7 @@ void ntpInit() {
|
||||
ts.add(
|
||||
TIME, 1000, [&](void*) {
|
||||
unixTime = getSystemTime();
|
||||
unixTimeShort = unixTime - START_DATETIME;
|
||||
if (unixTime < MIN_DATETIME) {
|
||||
isTimeSynch = false;
|
||||
// SerialPrint("E", "NTP", "Time not synched");
|
||||
|
||||
@@ -930,15 +930,15 @@ void IoTScenario::loadScenario(String fileName) { // посимвольно с
|
||||
File myfile = seekFile(fileName);
|
||||
if (myfile.available()) {
|
||||
strFromFile = new String("");
|
||||
|
||||
|
||||
String strFromF = myfile.readString();
|
||||
Serial.println(strFromF);
|
||||
jsonRead(strFromF, "scen", *strFromFile, true);
|
||||
myfile.close();
|
||||
|
||||
//Serial.println(*strFromFile);
|
||||
// Serial.println(*strFromFile);
|
||||
|
||||
if (strFromFile->length()) {
|
||||
if (strFromFile->length()) {
|
||||
getNextToken();
|
||||
while (strIterator < strFromFile->length() - 1) {
|
||||
// Serial.printf("-%c", LastChar);
|
||||
@@ -957,7 +957,6 @@ void IoTScenario::loadScenario(String fileName) { // посимвольно с
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
delete strFromFile;
|
||||
strIterator = 0;
|
||||
} else {
|
||||
@@ -968,7 +967,7 @@ void IoTScenario::loadScenario(String fileName) { // посимвольно с
|
||||
void IoTScenario::ExecScenario(String eventIdName) { // запускаем поочереди все корневые элементы выражений в сценарии, ожидаемо - это IFы
|
||||
// eventIdName - ID элемента для которого выполняем сценарий, т.е. игнорируем любые проверки, если нет такого ID в условиях
|
||||
isIotScenException = false;
|
||||
Serial.printf("Count root elements in scenario: %d\n", ScenarioElements.size());
|
||||
// Serial.printf("Count root elements in scenario: %d\n", ScenarioElements.size());
|
||||
for (unsigned int i = 0; i < ScenarioElements.size(); i++) {
|
||||
if (ScenarioElements[i] && ScenarioElements[i]->hasEventIdName(eventIdName)) ScenarioElements[i]->exec();
|
||||
// else Serial.printf("Call from ExecScenario: Skip ifexec because %s not found\n", eventIdName.c_str());
|
||||
|
||||
@@ -4,29 +4,67 @@
|
||||
class Loging : public IoTItem {
|
||||
private:
|
||||
String logval;
|
||||
String id;
|
||||
String fileName = "";
|
||||
|
||||
public:
|
||||
Loging(String parameters) : IoTItem(parameters) {
|
||||
jsonRead(parameters, F("logid"), logval);
|
||||
jsonRead(parameters, F("id"), id);
|
||||
}
|
||||
|
||||
void doByInterval() {
|
||||
String value = getItemValue(logval);
|
||||
size_t lines = 0;
|
||||
//если задано не правильное logid величины для логгирования
|
||||
if (value == "") {
|
||||
SerialPrint("E", F("Logging"), F("no value set"));
|
||||
SerialPrint("E", F("Loging"), F("no value set"));
|
||||
} else {
|
||||
//если время было получено из интернета
|
||||
if (isTimeSynch) {
|
||||
regEvent(value, "Logging");
|
||||
String logData = String(unixTime) + " " + value;
|
||||
addFileLn("/log.txt", logData);
|
||||
regEvent(value, "Loging");
|
||||
String logData = String(unixTimeShort) + " " + value;
|
||||
|
||||
static bool firstTime = true;
|
||||
//если зашли сюда первый раз то создаем файл с именем id-timestamp
|
||||
if (firstTime) {
|
||||
firstTime = false;
|
||||
createFileWithIdDatatimeName(logData);
|
||||
//если 2 ой раз и последующие разы
|
||||
} else {
|
||||
lines = countLines(fileName);
|
||||
if (lines <= 255) {
|
||||
addFileLn(fileName, logData);
|
||||
} else {
|
||||
createFileWithIdDatatimeName(logData);
|
||||
}
|
||||
}
|
||||
SerialPrint("i", F("Loging"), "loging in file (" + String(lines) + ") http://" + WiFi.localIP().toString() + fileName);
|
||||
|
||||
} else {
|
||||
SerialPrint("E", F("Logging"), F("cant logging - no time Synch"));
|
||||
SerialPrint("E", F("Loging"), F("Сant loging - time not synchronized"));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void createFileWithIdDatatimeName(String &logData) {
|
||||
fileName = "/logs/" + id + "-" + String(unixTimeShort) + ".txt";
|
||||
addFileLn(fileName, logData);
|
||||
SerialPrint("i", F("Loging"), "file created http://" + WiFi.localIP().toString() + fileName);
|
||||
}
|
||||
|
||||
void cleanLog() {
|
||||
String directory = "logs/" + id;
|
||||
auto dir = FileFS.openDir(directory);
|
||||
while (dir.next()) {
|
||||
String fname = dir.fileName();
|
||||
removeFile(directory + "/" + fname);
|
||||
SerialPrint("I", "Loging", fname + " deleted");
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
void* getAPI_Loging(String subtype, String param) {
|
||||
void *getAPI_Loging(String subtype, String param) {
|
||||
if (subtype == F("Loging")) {
|
||||
return new Loging(param);
|
||||
} else {
|
||||
|
||||
@@ -158,8 +158,39 @@ bool cutFile(const String& src, const String& dst) {
|
||||
return true;
|
||||
}
|
||||
|
||||
//функция считает количество строк в файле
|
||||
size_t countLines(const String filename) {
|
||||
size_t cnt = -1;
|
||||
String path = filepath(filename);
|
||||
auto file = FileFS.open(path, "r");
|
||||
if (!file) {
|
||||
return cnt;
|
||||
}
|
||||
file.seek(0, SeekSet);
|
||||
size_t size = file.size();
|
||||
size_t psn;
|
||||
do {
|
||||
cnt++;
|
||||
file.readStringUntil('\n');
|
||||
psn = file.position();
|
||||
} while (psn < size);
|
||||
file.close();
|
||||
return cnt;
|
||||
}
|
||||
|
||||
//удаляем файл
|
||||
void removeFile(const String& filename) {
|
||||
String path = filepath(filename);
|
||||
if (FileFS.exists(path)) {
|
||||
if (!FileFS.remove(path)) {
|
||||
SerialPrint("I", "Files", "remove " + path);
|
||||
}
|
||||
} else {
|
||||
SerialPrint("E", "Files", "not exist" + path);
|
||||
}
|
||||
}
|
||||
|
||||
//счетчик количества записей на флешь за сеанс
|
||||
void onFlashWrite() {
|
||||
flashWriteNumber++;
|
||||
SerialPrint(F("->"), F("FS"), F("write data on flash"));
|
||||
|
||||
Reference in New Issue
Block a user