Page 2 sur 3
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 09 mai 2023, 21:59
par Flying Domotic
Pour la RTC, il semble qu'il faille l'initialiser à une date non nulle avant de l'utiliser par un rtctime.set(). De plus, il est habile de le resynchroniser de temps en temps par un sntp.sync().
Sinon, quel est le pb avec le compteur ?
Avec MQTT, le plus simple est d'envoyer le compteur sous forme de string.
L'idée globale est d'enregistrer manuellement une valeur initiale, avec l'option "Retain".
Dans l'ESP, souscrire au topic du compteur. Lorsqu'on reçoit le topic, on l'incrémente et le republie avec la nouvelle valeur, toujours avec le flag "Retain".
De l'extérieur, on consulte le topic du compteur de temps en temps, et on regarde si ça change. si c'est le cas, c'est que l'ESP est s'est bien (re)connecté sur MQTT, et qu'il arrive à lire et écrire. Sinon, y'a un blème
Ca marche aussi bien pour un compteur incrémental que la date. Si on est joueur, on peut même utiliser une fonction "random" et écrire une valeur au hasard (à condition de vérifier qu'on initialise bien le random, par exemple avec une valeur lue sur A0 laissée en l'air).
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 10 mai 2023, 08:09
par pierrotori
const char* msg_veille=".";
StaticJsonDocument<200> doc;
pour mon problème de vatiable , j'ai dans le topic : { "value": "1"}
je fais ca pour le récupérer dans une variable de type
Code : Tout sélectionner
if (String(topic) == mqtt_veille) {
DPRINT("Valeur veille : ");
DPRINTLN(messageTemp);
// Deserialize the JSON document
DeserializationError error = deserializeJson(doc, messageTemp);
// Test if parsing succeeds.
if (error) {
DPRINT(F("deserializeJson() failed: "));
DPRINTLN(error.f_str());
return;
}
if (messageTemp == "") { msg_veille="."; }
if (messageTemp != "") { msg_veille = doc["value"]; }
DPRINT("Valeur lue : ");
DPRINTLN(msg_veille);
}
ensuite je fais ca alors que la variable contient bien 1
Code : Tout sélectionner
compteur=(int)(msg_veille)+1;
sprintf(mqttbuffer_var,"{ \"value\" : \"%d\" }", compteur );
client.publish(mqtt_veille, mqttbuffer_var, true);
et je me retrouve avec cette valeur : { "value": "1073671623"}
si j'arrive à le faire fonctionner je pourrais le faire sur la date et heure pour voir l'évolution des connections
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 10 mai 2023, 08:26
par pierrotori
je viens de trouver pour caster
Code : Tout sélectionner
sscanf(msg_veille, "%d", &compteur);
compteur=compteur+1;
sprintf(mqttbuffer_var,"{ \"value\" : \"%d\" }", compteur );
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 10 mai 2023, 10:41
par Flying Domotic
Effectivement, il vaut mieux récupérer une valeur numérique avant l'incrémentation.
Au niveau du code, il peut être intéressant d'utiliser "else" dans :
Code : Tout sélectionner
if (messageTemp == "") { msg_veille="."; }
if (messageTemp != "") { msg_veille = doc["value"]; }
qui deviendrait :
Code : Tout sélectionner
if (messageTemp == "") {
msg_veille = "0";
} else {
msg_veille = doc["value"];
}
Etant donné qu'on va convertir msg_veille en nombre, il peut être utile de lui donner une valeur numérique comme "0" plutôt que "." s'il n'est pas défini.
De même, protéger
par un
snprintf, voire un
, qui éviteront des soucis si le buffer mqttbuffer_var est trop court.
Ceci dit, on peut aussi créer le message de sortie par la classe ArduinoJson :
Code : Tout sélectionner
DynamicJsonDocument jsonDoc(50);
jsonDoc["value"] = compteur;
String jsonMessage;
serializeJson(jsonDoc, jsonMessage);
client.publish(mqtt_veille, jsonMessage, true);
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 10 mai 2023, 23:58
par pierrotori
Sympa la class Json pour créer une chaîne , du coup je peux faire jsonDoc["value"] = compteur;et jsonDoc["update"] = date;
merci pour l'info
Le compteur c'est bien mais ce n'est pas très parlant,
Je pourrais initialiser une date rtc_date dans mon topic veille avec la date du rtc au démarrage ou date de compilation et l'incremeter avec la durée cyclique de réveil de l'esp jusqu'à ce que la date de l'action existe (période très courte)
Pour rappel j'ai un topic action avec l'action demandée on ou off avec la date de l'action
Et un autre topic status avec l'action on ou off en cours et la date du status
Quand arrive ma demande d'action et qu'elle est différente du status alors je synchronise la rtc_date, ce qui veut dire que dans mon utilisation elle sera faite 2 fois par jour, le reste du temps elle sera incrementee
Cette gestion me permettra de voir que l'esp même en veille se connect même si il n'y a pas de demande car mon réseau a un niveau 1 la où se trouve l'esp
Je ne sais pas si la solution est bonne ou consommatrice mais de tout façon l'esp a chaque fois qu'il se réveille se connect au wifi et au mqtt, qu'en penses tu @flying ? As tu mis en place ce type de gestion ou une autre ?
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 11 mai 2023, 03:12
par Flying Domotic
De mon côté, je n'utilise pas trop la veille sur ESP. Si j'ai besoin d'un truc qui ne consomme pas trop, j'utilise plutôt un CC2652RB (ZigBee), qui possède un processeur séparé pour gérer les E/S et le temps, et ne réveiller le processeur principal que lorsqu'il y a besoin d'envoyer/recevoir des choses.. Côté consommation, c'est vraiment faible. Par contre, c'est pas forcement très simple à mettre en œuvre.
Sinon, pour monitorer MQTT, j'utilise un netstat sur le port 1883, et vérifie que les IP qui m'intéressent sont bien connectées. Dans ton cas, ça risque de ne pas trop le faire ...
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 12 mai 2023, 13:33
par pierrotori
Quand on a un topic qui contient cela
{
"value": "1.57",
"update": "2023-05-06 16:00"
}
si on veut remettre à jour uniquement la date c''est possible ou il faut réécrire la chaine complète ?
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 18 mai 2023, 19:03
par Flying Domotic
Ben ça dépend de la manière dont c'est traité ensuite. SI le(s) code(s) qui traie(nt) le topic s'attende(nt) à trouver les deux, la réponse est oui. Sinon ... c'est non.
Je dirais, dans le doute, qu'il vaut mieux réécrire le tout, surtout si le topic à une option "retain".
D'autant que si on le lit avant, il suffit juste de modifier l'item "udate" et de réécrire ce qu'on a lu avec cette modif.
Gestion On/off sur Esp8266 via MQTT
Publié : 24 mai 2023, 21:07
par pierrotori
Je galère a récupérer plusieurs topics dans la fonction callback avec json a cause des pointeurs de la fonction deserialization et les déclarations des variables char* ou char
Est ce quelqu’un pourrait mettre son code de la callback pour m’aider ?
Re: Gestion On/off sur Esp8266 via MQTT
Publié : 24 mai 2023, 22:21
par Flying Domotic
Par exemple :
Code : Tout sélectionner
void mqttMessageCallback(const char *topic, const char *payload, const AsyncMqttClientMessageProperties properties, const size_t len, const size_t index, const size_t total)
char localPayload[250];
size_t localSize = sizeof(localPayload);
if (len < localSize) localSize = len; // Maximize len to copy
memset(localPayload, '\0', sizeof(localPayload));
strncpy(localPayload, payload, localSize);
trace_info_P("Received MQTT message %s on topic %s, len %d, index%d, total %d", localPayload, topic, len, index, total);
// Check for long (multi packets) messages
if (len != total) {
trace_error_P("Can't deal with multi packet messages!");
return;
}
// Analyze JSON message
DynamicJsonDocument jsonDoc(MAX_SMS_MESSAGE_LEN);
auto error = deserializeJson(jsonDoc, localPayload);
if (error) {
trace_error_P("Failed to parse %s. Error: %s", localPayload, error.c_str());
return;
}
// Analyze topic
if (mqttGetTopic) { // Is mqttGetTopic defined?
if (String(topic) == mqttGetTopic) { // Is it the right topic?
String message = jsonDoc["message"].as<const char *>();
String number = jsonDoc["number"].as<const char *>();
if (message == "" && number == "") { // Check for message and number
trace_error_P("Message and number missing from MQTT payload %s for topic %s", localPayload, topic);
return;
}
if (message == "" ) { // Check for message
trace_error_P("Message missing from MQTT payload %s for topic %s", localPayload, topic);
return;
}
if (number == "") { // Check for number
trace_error_P("Number missing from MQTT payload %s for topic, %s", localPayload, topic);
return;
}
sendSMS(number.c_str(), message.c_str()); // Ok, store the SMS in queue
}
}
trace_error_P("Unknown topic %s received!", topic);
}