Recentemente ho avuto la necessità di poter controllare piGarden e piGuardian tramite protocollo mqtt in modo da potere avviare o fermare l’irrigazione da Home Assistant, il famoso software open source per la gestione domotica della casa.
A questo proposito ho creato un piccolo script python che funziona da subscribe per alcuni topic mqtt destinati a ricevere nei rispettivi payload i comandi delle api di piGarden e piGuardian e di inoltrarli ai rispettivi socket server. In pratica mqttconnector funziona da intermediario tra mqtt e piGarden/piGuardian.
Installazione
Per funzionare mqttconnector ha bisogno di alcune dipendenze, installiamole con i seguenti due comandi:
sudo apt-get install python2.7 python-pip sudo pip install paho-mqtt configparser
Scarichiamo ora mqttconnector da github:
cd git clone https://github.com/lejubila/mqttconnector.git
Aggiungiamo adesso il file relativo al servizio systemd che ci servirà successivamente per avviare mqttconnector e impostare l’avvio automatico al boot del sistema:
cd sudo cp mqttconnector/mqttconnector.service /etc/systemd/system/mqttconnector.service
Fate attenzione al percorso di mqttconnector.py indicato dentro /etc/systemd/system/mqttconnector.service che corrisponda alla posizione corretta dello script.
Configurazione
Copiamo il file di configurazione di esempio in /etc:
cd sudo cp mqttconnector/mqttconnector.ini.sample /etc/mqttconnector.ini
Adesso che abbiamo il nostro file di configurazione vediamo come è composto:
[mqtt] broker_address=_broker_hostname_or_ip_address_ port=1883 user=_broker_username_ password=_broker_password_ client_id=mqttconnector path_connector=/home/pi/mqttconnector/ subtopic_command=command subtopic_result=result [pigarden] enabled=1 host=_pigarden_socket_server_hostname_or_ip_addres_ port=_pigarden_socket_server_port_ exec_command=exec_cmd2sck.sh user=_pigarden_socket_server_username_ pwd=_pigarden_socket_server_password_ topic=pigarden result_enable=0 topic_result_qos=0 topic_result_retain=1 [piguardian] enabled=1 host=_piguardian_socket_server_hostname_or_ip_addres_ port=_piguardian_socket_server_port_ exec_command=exec_cmd2sck.sh user=_piguardian_socket_server_username_ pwd=_piguardian_socket_server_password_ result_enable=0 topic=piguardian topic_result_qos=0 topic_result_retain=1
Come possiamo vedere il file di configurazione è suddiviso in tre parti: mqtt, pigarden e piguardian.
La prima parte riguarda il protocollo mqtt e ci permette di indicare l’hostname/ip del broker e le credenziali di accesso. Oltre a questo dobbiamo indicare il path della directory dello script (path_connector).
Con subtopic_command indichiamo il subtopic su cui lo script riceverà i comandi delle api da inoltrare a piGarden/piGuardian.
Una vota che il comando è stato ricevuto tramite il subtopic_command, questo viene inoltrato al socket server della rispettiva applicazione e il risultato, se vogliamo, potrà essere pubblicato su un’ulteriore topic via mqtt. Questo topic sarà composto dal valore indicato in subtopic_result.
Avremo quindi i topic pigarden/command e piguardian/command tramite i quali mqttconnector ricecerà i comandi delle api da inoltrare ai socket server dei rispettivi software.
Sui topic pigarden/result e piguardian/result (se abilitato con il parametro result_enable) verrà pubblicato invece il risultato di risposta della chiamata api ricevuto precedentemente.
Esecuzione
Il metodo più opportuno per lanciare mqttconnector è utilizzare systemd. Ma prima magari può essere comodo eseguirlo manualmente in modo da avere a video l’output generato dallo script e verificare eventuali problemi di connessione al broker mqtt o altro. L’esecuzione manuale può essere fatta impartendo i seguenti comandi:
cd cd mqttconnector python mqttconnector.py
Se la connessione al server mqtt andrà a buon fine vedrete un output simile al seguente
192.168.1.251 mqtt_port mqtt_user mqtt_password Connected to broker subscribe: pigarden/command subscribe: piguardian/command
Continuando l’esecuzione in questa modalità potrete vedere anche l’output di eventuali chiamate alle api di piGarden/piGuardian impartite tramite protocollo mqtt.
Una volta che site sicuri che tutto funzioni per il verso giusto potrete interrompere l’esecuzione tramite Ctrl+C e riavviare mqttconnector utilizzando i comandi systemd:
sudo systemctl start mqttconnector
Inoltre per fare in modo che mqttconnector venga eseguito in automatico all’avvio del vostro Raspberry, dovete impartire il seguente comando:
sudo systemctl enable mqttconnector
Conclusione
Bene siamo arrivati alla conclusione. In un prossimo articolo vedremo come interfacciare piGarden a Home Assistant grazie proprio al protocollo mqtt.
Ciao sto provando mqttconnector,dove trovo una lista dei comandi da poter passare a pigarden?
Rinnovo i miei complimenti per il tuo lavoro
Ciao @Stefano,
ho appena pubblicato questo post relativo alle api di piGarden che dovrebbe fare al caso tuo.
Grazie appena possibile faccio i test del caso,se un giorno hai tempo pensa di poter integrare anche una seconda categoria di icone magari dei semplici switch,io attualmente uso pigarden anche per accendere l’illuminazione esterna.
Ciao David,
quale broker hai utilizzato?
Grazie in anticipo.
Ciao
@Paolo,
inizialmente ho usato il servizio online http://www.cloudmqtt.com, successivamente ho installato in locale mosquitto sul mio raspberry.
ciao ho aggiornato raspbian all’ultima versione e reinstallato tutto da zero, però quando tento di lanciare il comando
sudo systemctl start mqttconnector mi genera un errore
allora ho provato: sudo systemctl status mqttconnector.service e il risultato è questo
● mqttconnector.service – Home Assistant
Loaded: bad-setting (Reason: Unit mqttconnector.service has a bad unit file setting. )
Active: inactive (dead)
feb 26 14:28:12 raspberrypi systemd[1]: /etc/systemd/system/mqttconnector.service:6: Invalid user/group name or numeric ID:
feb 26 15:06:56 raspberrypi systemd[1]: /etc/systemd/system/mqttconnector.service:6: Invalid user/group name or numeric ID:
Ciao @marco,
puoi risolvere questo problema andando a sostituire la squente riga in /etc/systemd/system/mqttconnector.service
User=%i
con
User=pi
Ciao David
quest’anno ho voluto provare ad aggiungere il sensore di piaggia ed integrarlo con home assistant.
Il problema che ho riscontrato è con l’avvio del servizio mqttconnector che è che sembra non funzionare il comando “sudo systemctl enable mqttconnector”.
Al riavvio non vedo il servizio con “systemctl status” ma facendolo partire manualmente con “sudo systemctl start mqttconnector” va benissimo e funziona tutto.
in pratica ogni volta che si riavvia devo agire manualmente.
E’ un problema noto o sbaglio qualcosa?
Farti ancora i complimenti per me è un piacere visto che mi stai facendo divertire risolvendo un problema a mia moglie 🙂
Ciao @Cristiano,
hai provato a controllare nei log (/var/log/daemon.log) per vedere se hai qualche indicazione per cui mqttconnector non parte ll’avvio del sistema?
Una causa potrebbe essere che il servizio mqtt non è ancora partito perchi mqttconnector fallisce la connessione e muore.
Nel log restituisce un errore perchà il codice :
Traceback (most recent call last):
Apr 30 00:01:16 pigarden python[294]: File “/home/pi/mqttconnector/mqttconnector.py”, line 251, in
Apr 30 00:01:16 pigarden python[294]: client.connect(broker_address, port=port) # connect to broker
Apr 30 00:01:16 pigarden python[294]: File “/usr/local/lib/python2.7/dist-packages/paho/mqtt/client.py”, line 937, in connect
Apr 30 00:01:16 pigarden python[294]: return self.reconnect()
Apr 30 00:01:16 pigarden python[294]: File “/usr/local/lib/python2.7/dist-packages/paho/mqtt/client.py”, line 1071, in reconnect
Apr 30 00:01:16 pigarden python[294]: sock = self._create_socket_connection()
Apr 30 00:01:16 pigarden python[294]: File “/usr/local/lib/python2.7/dist-packages/paho/mqtt/client.py”, line 3522, in _create_socket_connection
Apr 30 00:01:16 pigarden python[294]: return socket.create_connection(addr, source_address=source, timeout=self._keepalive)
Apr 30 00:01:16 pigarden python[294]: File “/usr/lib/python2.7/socket.py”, line 575, in create_connection
Apr 30 00:01:16 pigarden python[294]: raise err
Apr 30 00:01:16 pigarden python[294]: socket.error: [Errno 101] Network is unreachable
Apr 30 00:01:16 pigarden systemd[1]: mqttconnector.service: Main process exited, code=exited, status=1/FAILURE
Apr 30 00:01:16 pigarden systemd[1]: mqttconnector.service: Failed with result ‘exit-code’.
è poco prima dell’attribuzione dell’indirizzo ip dal router quindi non trovandosi in LAN (via wifi) non riesce a raggiungere il broker.
Essiste un modo per ritardare l’esecuzione del servizio mqqtconnector o attendere la LAN via wifi?
Ciao David
ho risolto editando il /etc/systemd/system/mqttconnector.service in questo modo:
[Unit]
Description=Home Assistant
Wants=network-online.target
After=network-online.target
aggiungendo
Wants=network-online.target
dicendo che il servizio ha bisogno dell’apparato online per avviarsi
in questo modo si avvia non appena connesso alla LAN
Spero che possa essere utile in fase di progettazione e sviluppo.
Ciao e grazie ancora per farci usare il tuo progetto
Cristiano
buona sera, a me capita la stessa cosa di Cristiano, con il comando Start va, ma al riavvio del raspberry non funziona. La soluzione di Cristiano con me purtroppo non funziona.
Stavo pensando a qualcosa magari da aggiungere al crontab tipo un file controllo.sh che all’interno aspetta 30-40 secondi e se il servizio non è stato eseguito avvia sudo systemctl start mqttconnector, poi fa la verifica ed esce… Mi sai suggerire come fare dato che ho paura di impallare il raspy.
Ciao @marco,
l’avvio di mqttconnector viene eseguito tramite systemd e non tramite cron, quindi non possibile inserire uno script di attesa nel crontab.
Dovresti controllare i log per capire come mai il servizio mqttconnector non riesce a partire, forse non è ancora partito mosquitto?
Posto il log:
pi@raspberrypi:~ $ sudo systemctl status mqttconnector
● mqttconnector.service – Home Assistant
Loaded: loaded (/etc/systemd/system/mqttconnector.service; enabled; vendor preset: enabled)
Active: failed (Result: exit-code) since Thu 2020-07-16 19:55:41 CEST; 23min
Process: 478 ExecStart=/usr/bin/python /home/pi/mqttconnector/mqttconnector.py (code=exited, status=1/FAILURE)
Main PID: 478 (code=exited, status=1/FAILURE)
lug 16 19:55:41 raspberrypi python[478]: return self.reconnect()
lug 16 19:55:41 raspberrypi python[478]: File “/usr/local/lib/python2.7/dist-packages/paho/mqtt/client.py”, line 1071, in reconnect
lug 16 19:55:41 raspberrypi python[478]: sock = self._create_socket_connection()
lug 16 19:55:41 raspberrypi python[478]: File “/usr/local/lib/python2.7/dist-packages/paho/mqtt/client.py”, line 3522, in _create_socket_connection
lug 16 19:55:41 raspberrypi python[478]: return socket.create_connection(addr, source_address=source, timeout=self._keepalive)
lug 16 19:55:41 raspberrypi python[478]: File “/usr/lib/python2.7/socket.py”, line 575, in create_connection
lug 16 19:55:41 raspberrypi python[478]: raise err
lug 16 19:55:41 raspberrypi python[478]: socket.error: [Errno 101] Network is unreachable
lug 16 19:55:41 raspberrypi systemd[1]: mqttconnector.service: Main process exited, code=exited, status=1/FAILURE
lug 16 19:55:41 raspberrypi systemd[1]: mqttconnector.service: Failed with result ‘exit-code’.
Premetto che ho homeassistant su un raspberry pi4 con mosquitto che fa da broker con accesso alla rete via eterneth, e pigarden è installato su un’altro raspberry con mosquitto client e mqttconnector che si connette via wifi.
Prima con tutto installato in un raspberry funzionava correttamente, ora invece quando riavvio quello con pigarden devo lanciare manualmente il comando:
– sudo systemctl start mqttconnector e funziona tutto correttamente.
Avevo pensato ad un comando crontab che mi avvia un demone che tenta di far partire con sudo systemctl start mqttconnector e sta in sleep 10 secondi se non si attiva. quando ha attivato si stoppa però se non si può fare bisogna capire perchè
grazie
@marco
puoi provare a fare partire mqttconnector direttamente dal crontab dell’utente pi inserendo una entry come di seguito:
@reboot sleep 20; /usr/bin/python /home/pi/mqttconnector/mqttconnector.py
in questo modo attende 20 scondi prima di eseguire mqttconnector.
Grazie sei un idolo, funziona perfettamente 😀
il tuo progetto è favoloso, è già da un anno che lo utilizzo e da quando l’ho integrato con home assistant è semplicemente il top.
Ciao, quando faccio partire mqttconnector mi restituisce questo errore:
mqttconnector.service – Home Assistant
Loaded: bad-setting (Reason: Unit mqttconnector.service has a bad unit file setting.)
Active: inactive (dead)
mar 24 11:43:11 raspberrypi systemd[1]: /etc/systemd/system/mqttconnector.service:6: Invalid user/group name or numeric ID:
Ho provato gia’ a cambiare User=%i con User=pi ma niente da fare.
se lancio il comando python mqttconnector.py mi restituisce un risutato come quello riportato da te
Grazie per l’aiuto
@Marco,
prova a mettere
User=root
@lejubila,
niente da fare stesso errore… ma ho seguito la guida completamente..
192.168.178.150 1885 user_mqtt pass_mqtt
Connected to broker
subscribe: pigarden/command
subscribe: piguardian/command
Unexpected MQTT disconnection. Will auto-reconnect
Mi ritrovo con questo errore e lo ripropone in continuo. Tramite mqtt explorer non vedo nessuna connessione al broker mqtt.
Tutte le altre connessioni al broker funzionano correttamente.
Grazie
ciao
Ciao, se tento di aprire una valvola da Homeassistant si mqttconnecto ricevo questo errore:
192.168.178.150 1885 user pass
Connected to broker
subscribe: pigarden/command
subscribe: piguardian/command
Topic : pigarden/command
Message received: open Giardino_fronte_casa
pigarden command: open Giardino_fronte_casa
/home/pi/mqttconnector/exec_cmd2sck.sh: riga 7: _pigarden_socket_server_port_: S ervname non supportato per ai_socktype
/home/pi/mqttconnector/exec_cmd2sck.sh: riga 7: /dev/tcp/_pigarden_socket_server _hostname_or_ip_addres_/_pigarden_socket_server_port_: Argomento non valido
cat: -: Risorsa temporaneamente non disponibile
Command : ‘_pigarden_socket_server_username_
_pigarden_socket_server_password_
open Giardino_fronte_casa’
Command output :
Command exit status/return code : 1
Puoi autarmi??
Grazie
Da quello che vedo, nel file di configurazione mqttconnector.ini, non hai inserito i parametri di connessione al socket server di piGarden.
Ti ricordo infatti che per funzionare mqttconnector ha bisogno che sia abilitato e funzionante il socket server di piGarden.
Qui trovi maggiori dettagli per la configurazione di piGarden.sh e del socket server:
https://www.lejubila.net/2015/12/impianto-di-irrigazione-con-raspberry-pi-pigarden-lo-script-di-gestione-quinta-parte/
E qui trovi informazioni su mqttconnector:
https://www.lejubila.net/2018/12/mqttconnector-utilizza-le-api-pigarden-e-piguardian-tramite-mqtt/
192.168.178.150 1885 user pass
Connected to broker
subscribe: pigarden/command
Topic : pigarden/command
Message received: open Giardino_fronte_casa
pigarden command: open Giardino_fronte_casa
ho visto che mqttconnector riceve il comado da HA ma la valvola non si apre.
In mqttconnector.ini ho impostato cosi’
[pigarden]
enabled=1
host=172.0.0.1
port=8084
exec_command=exec_cmd2sck.sh
user=miouser
pwd=miapassw
topic=pigarden
result_enable=0
e in pigarden.conf ho configurato usertcp e passwtcp
ma dalla dashboard ricevo questo errore pigarden.Bad socket server credentials at line 131 of file /home/pi/piGardenWeb/app/PiGardenSocketClient.php
tolto user e pass funziona la dashboard.
Mi puoi fare un esempio di configurazioni? pigarde e pigardenweb girano sullo stesso raspberry, server mqtt su un nas esterno ad raspberry.
@maurizio
se imposti l’utente e password sul socket server dentro il file di configurazione di piGarden.sh, lo stesso utente e password devi metterlo nel file di configurazione di piGardenWeb, il file è /home/pi/piGardernWeb/.env
e devi impostare le seguenti variabili con l’utente e password impostato sul file di configurazione di piGardern.sh:
PIGARDEN_SOCKET_CLIENT_USER=miouser
PIGARDEN_SOCKET_CLIENT_PWD=miapassw
lo stesso utente e password lo devi mettere anche su mqttconnector.ini come hai gia fatto:
user=miouser
pwd=miapassw
attenzione però che su mqttconnector.ini il nome host è sbagliato e de essere
host=127.0.0.1
e non
host=172.0.0.1
fatte queste modifiche riavvia tutto per essere sicuro che i vari servizi abbiano recepito le modifiche inserite nei file di configurazione.
Ciao,
nelle distribuzioni linux più recenti c’è direttamente python3 installato, purtroppo ho visto che con questa versione di python lo script non funziona. Hai in programma di adattarlo? grazie