ESP8266: MQTT Publish Generator

Alle hier angegebenen Daten werden nicht über das Netzwerk übermittelt. Der Code wird direkt in deinem Browser erzeugt. Solltest du dennoch Bedenken haben, kannst du die Daten bzgl. deiner WiFi-SSID/-Kennwort auch auf Standard lassen. Die lassen sich im Script easy anpassen
Dieser Codegenerator erzeugt stumpfen Code, welcher per MQTT Sensoren und Aktoren an deinem Arduino im Netzwerk zur Verfügung stellt. Ja, es gibt eine anpassbare Loop-Funktion. Verlasse dich nicht darauf, dass das alles sauber ohne Anbindung an dein Wlan funktioniert.
Omas Beatmungsgerät gehört direkt an die Steckdose, nicht hinter diesen Code. Und schon gar nicht in CustomLoop()

Das kommt in naher Zukunft häufiger auf mich zu: ein Arduino (in meinem Fall ein NodeMCU ESP8266 [Amazon, kein Affiliate]) mit mehreren Buttons und Relays. Anbindung an Home Assistant über MQTT. Genutzt wird der PubSubClient als MQTT-Client.

Nach Angabe der Konfiguration wird im Browser ein Code generiert, der ggf. weiter angepasst werden kann und über die Arduino-IDE wie jeder andere Code geflasht werden kann. Ebenfalls generiert wird ein Template für Home Assistant, das einfach in die configuration.yaml eingebunden werden kann, um die entsprechenden INPUT-/OUTPUT-Pins im Zugriff zu haben.

Kurze Randnotiz: INPUT und OUTPUT bezieht sich aus Sicht von Home Assistant. Ein INPUT-GPIO ist zum Beispiel ein Taster. Ein OUTPUT-GPIO eine LED oder ein Relay. WiFi blinkt bei Verbindungsaufbau (400ms EIN, 400ms AUS) oder leuchtet durchgängig bei vorhandenem Wlan.

Verwendung der PINs
GPIO Beschriftung Board Verwendung Invertieren
GPIO00D3            
GPIO01TX            
GPIO02D4            
GPIO03RX            
GPIO04D2            
GPIO05D1            
GPIO06CLK            
GPIO07SD0            
GPIO08SD1            
GPIO09SD2            
GPIO10SD3            
GPIO11CMD            
GPIO12D6            
GPIO13D7            
GPIO14D5            
GPIO15D8            
GPIO16D0            
WiFi-Daten
MQTT-Server
MQTT Client-spezifisch
Offline-Modus
Verzögerungen
ms
ms
* lassen sich auch in den ersten Zeilen des Codes easy anpassen, falls Bedenken bzgl. der Sicherheit der hier eingegebenen Daten bestehen

Am Ende des Codes findet sich übrigens eine „CustomLoop“. In dieser kann direkt auf die Input-/Output-GPIOs zugegriffen werden und der Status verändert werden. Im Falle von Output-GPIOs wird der Status auch direkt über MQTT aktualisiert – schaltet ihr in der CustomLoop eine LED ein, bekommt dies euer HomeAssistant ebenfalls mit. Bitte beachte, dass, wenn keine Verbindung zum MQTT-Broker vorhanden ist, ggf. diese Funktion nur sehr selten (etwa ein mal alle 30 Sekunden) aufgerufen wird.

Falls dich ein paar Erklärungen zum Code interessieren, fange ich mal mit den INPUT-GPIOs an:

  • für jeden GPIO gibt es eine Variable, die den letzten Status enthält
  • Bei Veränderung des INPUTs (kurzgeschlossen / nicht kurzgeschlossen) wird eine MQTT-Nachricht gesendet
  • der letzte Status wird sich gemerkt
  • Repeat

Für jeden INPUT-GPIO gibt es eine eigene Funktion. Diese lautet "CheckButtonX", wobei X der GPIO ist. Wenn du angegeben hast, dass 5 ein INPUT ist, gibt es definitiv eine Funktion "CheckButton5", die den aktuellen Status von 5 mit der Variable Button5State gegengleicht und erkennt, ob sich der Status von GPIO 5 geändert hat.

Die OUTPUT-GPIOs sehen etwas anders aus. Die haben zwar auch Variablen im selben Namensschema wie INPUT (z.B. Button12State), aber die sind nur dafür da, um in CustomLoop zu erkennen, ob du doch noch mal irgendwo Spannung angelegt hast. Die werden in der Funktion OnMQTTMessage gegengeprüft und dementsprechend geschaltet. Alle OUTPUT-GPIOs werden in der Funktion OnMQTTMessage verwaltet. Die wird, PubSubClient sei Dank, bei jeder eingehenden MQTT-Nachricht, die subscribed ist (was automatisch der Fall ist, wenn ein PIN auf OUTPUT steht, egal) aufgerufen. Da wird geguckt, ob ON oder OFF gesendet wird, und der PIN dementsprechend LOW oder HIGH geschaltet.

Es gibt eine zentrale Funktion ReportMQTTState. Die wird jedes mal aufgerufen, wenn du in CustomLoop den Status eines OUTPUTs änderst oder wenn der letzte Aufruf [inklusive Änderung von GPIOs durch dich] mindestens 15 Sekunden her ist. Die dient dazu, dass andere IoT-Geräte nicht der Meinung sind, dass der Arduino ein Timeout hat. Und halt, um den aktuellen Status von GPIOs zu übermitteln. Musst du dich nicht drum kümmern. Nutze einfach die CustomLoop, schreibe da sowas rein wie digitalWrite(5, digitalRead(4) || digitalRead(12) ? HIGH : LOW) und sei glücklich, dass alles sauber an Home Assistant übertragen wird.

Die Funktion CustomLoop wird in der Standard-Config nur aufgerufen, wenn WiFi vorhanden ist. Wenn du kein WLAN hast, was du nutzen möchtest (und damit durch diesen Generator ein paar Zeilen Code generierst, die du sowieso wieder löscht, lass es in dem Fall einfach) wird die nicht funktionieren. Standardmäßig funktioniert die nur, wenn WLAN und Anbindung an den MQTT-Broker i.O. sind. Sonst nicht. Keine Ahnung, installiere dann Tasmoto, wird schon schief gehen. Aber dieser Codegenerator braucht dringend eine Verbindung zum WLAN und zum MQTT-Broker, um sauber zu laufen.

Das Script nimmt an Ressourcen, was es bekommt. Es unterstützt kein Deep Sleep, ohne größere Anpassungen vorzunehmen. Wenn du der Meinung bist, dass Strom sowieso zu teuer ist, kannst du ganz am Ende der loop() ein Delay einbauen. Das kann das Script ab. Für DeepSleep habe ich abgefuckte Schaltungen mit Kondensatoren und XOR-Gattern gesehen, das würde zwar auch in so einen simplen Code-Generator machbar sein, aber auch automatisch ein paar Seiten an Anleitungen mitgenerieren müssen. Dafür bin ich zu faul.

Mehrere OUTPUTs, INPUTs, und WiFis sind möglich. Ich weiß nicht, was ich mal brauche, vielleicht möchte ich mal einen Radiowecker starten, wenn mein Türschloss keine Verbindung mehr zum WLAN hat. Auf dem Weg kann ich sowohl immer 400 Sekunden am Stück (mit 400 Sekunden Pause zwischendrin) den Wecker hören, als auch eine LED in einem verbauten Kasten (nicht) angucken. Praktisch. Ist gewollt, dass man mehr WLAN-LEDs angeben kann, aber je mehr ich drüber nachdenke umso dümmer klingt das. Ist dennoch möglich.

Kategorien: Arduino, Home Assistant