Hardware and software solution for automated hydroponics system controller
Raspberry pi 2w: Raspberry PI OS LITE (64-bit); no desktop Raspberry pi 4: Raspberry PI OS LITE (64-bit); no desktop
Rendszer frisítése:
sudo apt updatesudo apt upgradeGit telepítése:
sudo apt-get install gitKönyvtár klónozása:
sudo git clone https://github.com/DanielBrenn/Hydroponics-systems.gitEz későbbiekben különbőző kiegészítők telepítéséshez
sudo apt-get install nodejs npmHa előzetesen volt telepítve docker container, akkor a következő parancssorral lehet lecserélni a régi verziót:
$ for pkg in docker.io docker-doc docker-compose podman-docker containerd runc; do sudo apt-get remove $pkg; doneEzután mivel nincs desktop környezet ezért a következő módon lehet a docker conatinert telpíteni:
# Add Docker's official GPG key:
sudo apt-get update
sudo apt-get install ca-certificates curl
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/debian/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc# Add the repository to Apt sources:
echo \
"deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/debian \
$(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
sudo apt-get update# Install docker container
sudo apt-get install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-pluginLegkönnyebben a különböző konténerek https://hub.docker.com/ oldalon találhatóak meg összefoglalva
A konténerek kezeléséhez webalapú kezeléséhez:
docker pull portainer/portainer-ce:linux-arm A vezérlésért felelős grafikus felületen progrmaozható node-red (későbbiekben lesz telepítve docker konténeren kívül oka: lásd később):
nodered:
ocker pull nodered/node-red
Mqtt borker mosquitto
docker pull eclipse-mosquittoData platform influxDB
docker pull influxdb:latestData visualisation grafana
docker pull grafana/grafanaFontos megjegyezni, hogy minden egyes konténer egymástól függetlenül fut. Tulajdonságaik ezeknek a konténereknek: - Minden konténer saját erőforrásokkal rendelkezik->ha egy konténer összeomlik nem befolyásolja a többi modult - Saját virtuális hálózatot alkot (egyedi IP cím) - A hálózatokat docker konténer egy virtuális switch-el köti össze->egy konténerek között van lehetőség TCP/IP protocollal kommunikálni, de konténeren kívülre sükséges a prot forwarding
Első lépésként beállítjuk a "restart policies" azaz megadjuk, hogy hogyan induljonanak el docker containerek indításkor. Cél az, hogy esteleges hiba esetén, illetve indításkor automatikus elinduljon.
IO kezeléséhez kell majd
sudo docker run -d -p 8888:8888 --privileged --name gpiod corbosman/pigpiod
A konténereken belüli file rendszer eléréséhez
sudo docker run -ti -v $(pwd):/mnt ubuntu bashsudo docker run -d -p 9000:9000 --name=portainer --restart=always -v /var/run/docker.sock:/var/run/docker.sock -v portainer_data:/data portainer/portainer-ce:linux-armsudo docker run -t -d -p 3000:3000 --name frontend --restart unless-stopped grafana/grafanasudo docker run -t -d -p 1880:1880 --restart unless-stopped -v /home/nodereddata:/data --name logic nodered/node-redsudo docker run -t -d -p 8086:8086 --name database --restart unless-stopped influxdb:latesthttps://github.com/sukesh-ak/setup-mosquitto-with-docker • Létre kell hozni a követekző mappa rendszert, hogy a futás közben generált adatokat a docker containerből kimentse a mosquitto-docker
mkdir -p ~/mosquitto/config
mkdir -p ~/mosquitto/data
mkdir -p ~/mosquitto/log•Manuálisan létre kell hozni a következő szetup filet:
nano ~/mosquitto/config/mosquitto.confA fájlba a következő beállítási paramétereket kell írni (autentikáció nélkül)
persistence true
persistence_location /mosquitto/data/
log_dest file /mosquitto/log/mosquitto.log
persistence_file mosquitto.db
listener 1883
allow_anonymous true•Autentikáció esetén (Alternatív beállítás) mosquitto.conf: -allow_anonymous false -password_file /mosquitto/config/pwfile
touch ~/mosquitto/config/pwfile# login interactively into the mqtt container
sudo docker exec -it <container-id> sh
# Create new password file and add user and it will prompt for password
mosquitto_passwd -c /mosquitto/config/pwfile user1
# Add additional users (remove the -c option) and it will prompt for password
mosquitto_passwd /mosquitto/config/pwfile user2
# delete user command format
mosquitto_passwd -D /mosquitto/config/pwfile <user-name-to-delete>A jelszó beállítása a következő paranccsal történik: "mosquitto_passwd"
•Végül el kell indítani a Mosquitto broker containert:
docker run -d -t --name mosquitto --restart unless-stopped -p 1883:1883 -v ~/mosquitto/config:/mosquitto/config -v ~/mosquitto/data:/mosquitto/data -v ~/mosquitto/log:/mosquitto/log eclipse-mosquitto•Mosquitto cliens telepítése teszteléshez:
sudo apt install mosquitto-clientsRészek funkciója: --restart: esetleges leállást, hogyan kezelje a docker -v: a conténer mapparendszerét myNodeREDdata a konténeren kívülli rendszer mapparendszerrel /data (conténer:külső mappa) --device: elérhetővé tesz a konténer számára konténeren kívüli erőforrások/mappák elérést Forrás: https://nodered.org/docs/getting-started/docker https://docs.docker.com/reference/cli/docker/container/run/#device
Indítás után a következő címeken érhetőek el a konténerek:
•Portainer: https://raspberrypi.local:9443/
•Grafana: raspberrypi.local:3000/
•Node Red: raspberrypi.local:1880/
•InfluxDB: raspberrypi.local:8086/
•Mosquitto: raspberrypi.local:1883/
Ez a funkció a későbbiekben a kész termék meglévő hálózatba való integrálásnál fogja betölteni a szerepét. Működése: az operációs rendszer felállása után közvetlenül az RPI lefuttat egy python scriptet, ami egy interupton keresztül (trigger high->low átmenet) figyeli GPIO4-es pint.
Elsőként létre kell hozni a scriptet ami lefut amikor elindul az operációs rendszer: Projekt mappába navigálunk:
cd /
cd/home/Hydroponics-systemsA létehozzuk a launcher filet ami meghívja majd a scriptet
sudo nano launcher.shTartalma: cd/ cd home/rpi4/Hydroponics-systems sudo python3 access-point-set.py cd/
access-point-set file tartalma:
import RPi.GPIO as GPIO
import os
import time
BUTTON_GPIO = 17
GPIO.setmode(GPIO.BCM)
GPIO.setup(BUTTON_GPIO, GPIO.IN, pull_up_down=GPIO.PUD_UP)
print("Script has started")
GPIO.wait_for_edge(BUTTON_GPIO, GPIO.FALLING)
print("Button was pushed")
os.system("sudo nmcli device disconnect wlan0")
os.system("sudo nmcli device up wlan0")
os.system("sudo nmcli device wifi hotspot ssid rpi4 password 12345678")
GPIO.cleanup()
Hydrophonics mapában létrehozunk egy log nevezetű mappát
Magát a launcher.sh corntrab háttérben futó sprogrammal lesz időzítve
sudo crontab -e@reboot sh /home/rpi4/bbt/launcher.sh >/home/rpi4/logs/cronlog 2>&1
Az MQTT egy publis-subscribe alapon működő kommunikációs protokol, ahol az eszközök/adatgyűjtők (edge devices) egy központi szerverhez kapcsolódnak (MQTT broker) amin keresztül különböző topikokra/témákra iratkoznak fel. Adott eszközök adott topikokra iratkoznak fel az MQTT brokeren keresztül, így az eszközök kommunikáció szempontjából el vannak egymástól választva a broker által.
A topic azonosítja a kommunikációt pontosabban az elérendő információt, a feriatkozott eszközök között teremt kapcsolatot valamilyen tetszőleges logika szerint. Más szavakkal a topic információt címez meg tetszőleges logikával és ez az infromációt csak az arra feliratkozott eszközök érhetik el- ez képzi a kommunikációs csatornát. Egy topik egy eszköz számára lehet írható (publish), olvasható(subscribe) vagy egyszerre a kettő. Egy topic több eszköz által is elérhető lehet. A topicoc hierarhicus vagy többszintetes információ azonosítást tesz lehetővé.
Szintek közötti alárendeltség:
level1/ level2a/ level3a1 ...
level1/ level2b ..
level1/ level2c ...
level1/ level2d ...
level1/ level2d/ level3d1 ...
level1/ level2d/ level3d2 ...
level1/ level2d/ level3d3 ...
level1/ level2d/ level3d4 ...
Hidroponiás rendszer esetében a következő struktúra lesz alkalmazva:
{% rowheaders %}
| level1 | level2 | level3 |
|---|---|---|
| DataCol | DataType | DataValue |
{% endrowheaders %}
Ahol: DataCol - Adatgyűjtőt azonosítja DataType - Az eszköz adattípusát (3 féle): Jelenlegi érték (Current), Beállított érték (SetVal)(ha van), Kalibrációs és Jelleggörbe paraméterek (FunParam) (ha van)
{% rowheaders %}
|---------|---------|-----------|
| Current | SetVal | FunParam |
|---|---|---|
| ECstate | ECset | ECcp1V |
| ECcp2V | ||
| ECcp1CONC | ||
| ECcp2CONC | ||
| Phstate | Phset | PHcp1V |
| PHcp2V | ||
| PHcp1PH | ||
| PHcp2PH | ||
| NO3state | NO3set | NO3cp1V |
| NO3cp2V | ||
| NO3cp2CONC | ||
| NO3cp1CONC | ||
| Kstate | Kset | Kcp1V |
| Kcp2V | ||
| Kcp1CONC | ||
| Kcp2CONC | ||
| Castate | Caset | Cacp1V |
| Cacp2V | ||
| Cacp1CONC | ||
| Cacp2CONC | ||
| Mgstate | Mgset | Mgcp1V |
| Mgcp2V | ||
| Mgcp1CONC | ||
| Mgcp2CONC | ||
| Kstate | Kset | Kcp1V |
| Kcp2V | ||
| Kcp1CONC | ||
| Kcp2CONC | ||
| WTstate | WTset | Wvolume |
| Whp | ||
| ATstate | ATset | RV |
| HSP | ||
| AHstate | AHset | RV |
| HP | ||
| WLstate | WLset | WContCross |
| WlevSenOFFset | ||
| PPI1state | - | PPparam1 |
| PPI2state | - | PPparam2 |
| PPI3state | - | PPparam3 |
| PPI4state | - | PPparam4 |
| PPI5state | - | PPparam4 |
| RecPumpstate | RecWCurset | RecPumpParam |
| MixPumpstate | MixWCurset | MixPumpParam |
{% endrowheaders %}
Oka: mivel a konténeren belüli elemek nem képesek elérni közvetlenül a kernell szintű elemeket így a Node-red nem képes kiegészítő lépések nélkül vezérelni a GPIO portokat. Az előbb emített kiegészítő lépések minden egyes egyedi funkció/könyvtár telepítésénél szükséges elvégezni, emiatt új könyvtárak telepítése megnehezül, illetve minden könyvtár esetében egyedileg kell megoldani, hogy a kernell megfelelő részét elérje az adott modul/könyvtár.
Először navigáljuk a projekt könyvtárba
cd /home/rpi4/Hydroponics-systems/Következő lépésben telepítjük a Node-Red modult:
bash <(curl -sL https://raw.githubusercontent.com/node-red/linux-installers/master/deb/update-nodejs-and-nodered)Majd beállítjuk, hogy a rendszer indításakor elinduljon a Node-red modul
sudo systemctl enable nodered.serviceFontos !! Node-red innetől kezdve a lokális hálózaton elérhető bárki által!!
•Node-Red indítása
node-red-start•Node-Red beállítása:
node-red admin init•Node-red eléréshi címe+port szám localhost:1880 •Important folders: Password management /etc/sudoers.d/010_pi-nopasswd Install-log: /var/log/nodered-install.log
Eddigekben a Node-red apaverziója lett telepítve, ami még nem alkalmas a RPI I/O pinjeinek a kezelésére, illetve nem tartalmazza még a kommunikációhoz szüksége protokoll csomagokat.
Modulok Node-Red: •node-red 4.0.9
•node-red-contrib-ads1x15_i2c 0.0.14
•node-red-contrib-buffer-parser 3.2.2
•node-red-contrib-dht-sensor 1.0.4
•node-red-contrib-ds18b20-sensor 1.3.6
•node-red-contrib-influxdb 0.7.0
•node-red-contrib-play-audio 2.5.0
•node-red-node-pi-gpio 2.0.6
•node-red-node-ping 0.3.3
•node-red-node-pisrf 0.4.0
•node-red-node-random 0.4.1
•node-red-node-serialport 2.0.3
•node-red-node-smooth
PIGPIO telepítése, hogy lehessen használni az alacsonyabb szintűbb funkciókat (interrupt timer)
sudo npm install pigpioHozzáférést kell biztosítani pigpio-nak, hogy ne kelljen sudo paranccsal meghívni az írt funkciókat amik a pigpio-t használ (problémát jelent mert sudo az újra meghívja és újpróbálja indítani pigpio-t ami hibát fog okozni)
sudo visudoA fájlba (visudo) a legvégére ezt be kell helyezni:
rpi4 ALL=(ALL) NOPASSWD: /usr/bin/nodeDHT-11 szenzor:
sudo npm install --unsafe-perm -g node-red-contrib-dht-sensorEhhez szüksége kiegészíteni
Következő módon lehet elérni a NODE-Red konténer belsejét (közvetlenül nem lehet CMD-ből elérni):
sudo docker exec -it logic bash GPIO kezeléséhez telepíteni kell:
npm install node-red-contrib-gpioGPIO telepítése kernell szinten: Első lépésként navigéljunk a raspberry pi gyökérkönyvtárába:
sudo apt install git
git clone https://github.com/WiringPi/WiringPi.git
cd WiringPi
./build debian
mv debian-template/wiringpi_3.14_arm64.deb .
sudo apt install ./wiringpi_3.14_arm64.deb GPIO kezeléséhez: sudo apt-get install python3-rpi.gpio
Az InfluxDB felelős az időben rögzített (time-series data) adatok rendszerezéséért és tárolásáért. Fontos megjegyezni InfluxDB v2 volt használva, mind a Node-Red, mind a Grafanaval való kapcsolatnál fontos lesz. Az adatokat a következő logika szerint tárolja:
-
Bucket (CalibData, MQTTTDEV, SetValue, Measurment): ez fogja össze az összes mért adatot fő gyűjtő kategória,
-
•Mesurment(Tesdata_n): alkategória amely a mérési adatcsomagokat választja szét jelen esetben különböző mérőkörökből (különálló rendszerből álló) adatokat foglalja össze •Field: mérési adattípusok szerint választja szét (pl. víz hőméréskletet(WTstate) és a levegő hőmérsékletet(ATstate) választja szét kategóriákra) •Tags: az adatokhoz kapcsolt metaadat ami az adatok további szűrésére szolgál (nem volt használva) •Timestamp: minden adatponthoz hozzá van rögzítve Ezek együttesen azonosítják az adatokat.
Beállításhoz el kell navigálni http://localhost:8086 címre vagy ha nem működik meg kell keresni a RPI IP címét hostname -i consol parancsal és a localhost helyére kell írni a parancs által adott ip címet. Ezután a következő lépéseket kell megtenni.
- Be kell állítani az autentikációt
- kreálni kell egy új Organizációt (Testing) (Később ehhez fogja küldeni az adatokat a Node-Red gyakorlatilag egy külön gyűjtő paraméter, amelyhez tartozik hozzáférési jogokkal rendelkezik)
- Kreálni kell egy bucketet (TESTINGBUCKET) (Fő gyűjtő kategória)
- Kreálni kell egy a buckethez tartozó api token-t/kulcsot írási és olvasási joggal (InfluxDB v2 sajátossága)
A kommunikáció megvalósításához több feltételnek teljesülnie kell. •Szükséges ismerni, hogy az InfluxDB milyen ip címe érhető el: http://localhost:8086 (Docker container beállításánál) •Szükséges a kiválasztott bucketnek generált access token (InfluxDB ben kell beállítani) •Ismerni kell az InluxDB Organization ID-t (EZ fogja azonosítani, hogy melyik "felhasználóhoz" fusson be az adat) (InfluxDB ben kell beállítani), •Bucket nevére, melyik bucketbe lesz egységesen gyűjtve az adat, (InfluxDB ben kell beállítani). •Measurment milyen measument néven lesz mentve az adott rendszerből származó adatot (Node-Red-től érkezik).
