Mündəricat:
2025 Müəllif: John Day | [email protected]. Son dəyişdirildi: 2025-01-13 06:56
Teorik olaraq, hər dəfə səhər fincanınız üçün qəhvə maşınına getdiyiniz zaman su çənini doldurmaq üçün yalnız iyirmi bir şans var. Ancaq praktikada görünür ki, maşın birtəhər bu işi sizin üzərinizə qoymaq üçün bir yol tapır. Qəhvə nə qədər çox istəsən, qorxulu "su qabını doldur" mesajını almaq ehtimalı daha yüksəkdir. Həmkarlarım da bu mövzuda eyni fikirdədirlər. Əlimizdən gələni əsirgəməyənlər olaraq, buna son qoyacaq texnologiyanı tətbiq etməyə qərar verdik.
Təchizat
Avadanlıqlarımız
SAECO Aulika Focus qəhvə maşınımız var. Bu günə qədər, standart 5 Gallon (19L) su şüşəsindən maşının su anbarını doldurmaq üçün əl nasosu istifadə etdik.
Məqsədlərimiz
- Bir röle vasitəsilə bir növ nəzarətçi və ya mikro kompüter tərəfindən idarə olunan elektrik nasosundan istifadə edin.
- Qəhvə maşınının tankındakı suyun səviyyəsini ölçmək üçün bir yol tapın ki, sistemimiz onu nə vaxt dolduracağını bilsin.
- Sistemə, tercihen mobil cihazdan real vaxt rejimində nəzarət etmək vasitələrinə sahib olun.
- Sistemdə bir şey səhv olarsa bildirişlər alın (Slack və ya oxşar xidmət vasitəsilə).
Addım 1: Avadanlıq seçimi
Pompa
Sürətli bir veb axtarış, seçdiyiniz su şüşəsi üçün hazırlanmış bir neçə elektrik nasos modelini göstərəcəkdir. Belə nasoslar ümumiyyətlə ON/OFF açarı ilə idarə olunur (məsələn, Hot Frost A12 və ya SMixx ХL-D2). Budur layihəmiz üçün seçdiyimiz nasos.
Nəzarət cihazı
Bir neçə cihazı sınadıq, lakin aşağıdakı üstünlüklərə görə bir Raspberry Pi üzərində yerləşdik:
- Yaxınlıq sensoru bağlamağa imkan verən bir GPIO var
- Python dəstəkləyir
Raspbian Buster Lite -in yeni bir versiyasını və Python 3 -ü işə salmaq üçün lazım olan hər şeyi quraşdırdıq.
Pompanı necə dəyişdiririk
Gücü idarə etmək üçün alternativ cərəyan üçün uyğun olan orta güc (12V/2A) bərk hal rölesini seçdik. Röleyi nasosu elektrik prizinə bağlayır və Raspberry Pi -nin rəqəmsal pimi ilə idarə olunur.
Suyun səviyyəsini necə yoxlayırıq
Qəhvə maşınının konstruksiyasını dəyişdirməmək bizim üçün vacib idi, buna görə suyun səviyyəsini ölçmək üçün HC-SR04 Ultrasonik yaxınlıq sensoru istifadə etməyə qərar verdik.
Sensor yayıcıları üçün iki delikli xüsusi bir su çəni qapağını 3d çap etdik. Sensor üçün GitHub kitabxanasını asanlıqla tapdıq və bu anda bütün hazırlıq işləri başa çatdı.
Addım 2: Sistemin dizaynı
Sistemin Məntiqi
Sistem aşağıdakı sadə məntiq nəzərə alınmaqla hazırlanmışdır:
- Sistem, sensor və su səthi arasındakı məsafəni daim izləyir.
- Nə vaxt ki, məsafə dəyişikliyi eşik dəyərini keçərsə, sistem öz vəziyyəti haqqında məlumatı buluda göndərir.
- Məsafə icazə verilən maksimum həddən artıq olarsa (tank boşdur), sistem nasosu işə salır və məsafə icazə verilən minimum dəyərdən az olduqda onu söndürür.
- Sistemin vəziyyəti dəyişəndə (məsələn, nasos işə düşür) buluda məlumat verir.
Səhv olarsa, Slack kanalına bildiriş göndərilir.
Qəhvə maşını boşdaykən, sistem bulud xidmətinə hər dəqiqədə bir dəfə diaqnostik məlumatlar verir. Əlavə olaraq, vəziyyətini hər 5 dəqiqədə bir buluda göndərir.
Pompa aktiv olduqda sistem məlumatları daha tez -tez göndərir, lakin hər yarım saniyədə bir dəfədən çox deyil.
def send (bulud, dəyişənlər, dist, error_code = 0, güc = Yanlış): pump_on = is_pump_on () faiz = calc_water_level_percent (dist) dəyişənlər ['Məsafə'] ['dəyər'] = uzaq dəyişənlər ['Su səviyyəsi'] [' dəyər '] = yüzdə dəyişənlər [' PumpRelay '] [' dəyər '] = pompa_on dəyişənlər [' Status '] [' dəyər '] = calc_status (səhv_kodu, faiz, nasos_on)
cari = vaxt ()
qlobal son_ göndərmə_ vaxtı güc və ya cərəyan olarsa - son_ göndərmə_ vaxtı> MIN_SEND_INTERVAL: oxunuşlar = cloud.read_data () cloud.publish_data (oxunmalar) last_sending_time = cari
Pompa ilə işləmək
Aşağıdakı sabitləri nasosun işləmə məntiqi üçün əsas olaraq təyin edirik.
# GPIO Pinləri (BCM) GPIO_PUMP = 4 GPIO_TRIGGER = 17 GPIO_ECHO = 27
# Pompa
START_PUMP = 1 STOP_PUMP = 0 PUMP_BOUNCE_TIME = 50 # milisaniyə PUMP_STOP_TIMEOUT = 5 # saniyə
Vacibdir: Pin 4-dən istifadə edəcəksinizsə, münaqişələrin qarşısını almaq üçün 1-Telli raspi-config seçimini deaktiv etməyi unutmayın.
Proqramın başlanğıcında bir geri çağırma qeyd edirik və ilkin vəziyyəti OFF olaraq təyin edirik.
Pompanı dəyişdirən funksiyanın kodu budur:
def toggle_pump (dəyər): pump_disabled olduqda: is_pump_on ()! = dəyər: log_debug ("[x] % s" % ("BAŞLAT 'əgər başqa dəyər' DUR ')) qaytar GPIO.setup (GPIO_PUMP, GPIO. OUT) GPIO.output (GPIO_PUMP, dəyər) # Tökməyə başla/dayandır
Yuxarıdakı başlanğıc kodunda göstərildiyi kimi, röle AÇILDIĞI zaman, aşağıdakı geri çağırış çağırılır:
pump_on = Yanlış def pomp_relay_handle (pin): global pump_on pump_on = GPIO.input (GPIO_PUMP) log_debug ("Pompa rölesi % d olaraq dəyişdirildi" % pump_on)
Geri çağırışda, nasosun mövcud vəziyyətini dəyişənə saxlayırıq. Tətbiqin əsas döngəsində, nasosun aşağıda göstərildiyi kimi keçid anını aşkar edə bilərik:
def is_pump_on (): global pump_on return pump_on
əgər GPIO.event_detected (GPIO_PUMP):
is_pouring = is_pump_on () #… log_debug ('[!] Pompa hadisəsi aşkarlandı: % s' % (Başqa bir şey tökülsə 'Açıq')) göndər (bulud, dəyişənlər, məsafə, güc = Doğru)
Məsafənin ölçülməsi
Ultrasonik yaxınlıq sensoru istifadə edərək su səthinə olan məsafəni ölçmək olduqca asandır. Depomuzda bir sensoru sınamağa imkan verən bir neçə python skriptini paylaşdıq.
Həqiqi tətbiqlərdə, sensorun sıçrayış təsiri və su salınımları səbəbindən sensor oxunuşları dəyişə bilər. Bəzi hallarda oxunuşlar tamamilə yox ola bilər. N son dəyərləri toplayan, zirvələri atan və qalan ölçülərin ortalamasını hesablayan bir BounceFilter sinifini tətbiq etdik. Ölçmə prosesi aşağıdakı asinxron alqoritmlə həyata keçirilir.
# Son sensor ölçmələrini saxlayır = BounceFilter (ölçüsü = 6, discard_count = 1)
read_complete = threading. Event ()
def wait_for_distance ():
read_complete.clear () thread = threading. Thread (target = read_distance) thread.start ()
oxunmursa_tamam et. gözləyin (MAX_READING_TIMEOUT):
log_info ('Oxu sensoru zaman aşımı') qaytar Yoxdur oxunuşlar.avg ()
def read_distance ():
cəhd edin: dəyər = hcsr04.raw_distance (sample_size = 5) yuvarlaqlaşdırılmış = dəyər əgər heç bir dəyər yoxdur Yuvarlaq (dəyər, 1) readings.add (yuvarlaq) istisna istisna olmaqla, səhv: log_error ('Daxili səhv: % s' % səhv): oxu_complete.set ()
Filtrin tam tətbiqini mənbələrdə tapa bilərsiniz.
Addım 3: Fövqəladə Halların Müalicəsi
Sensor yanarsa və ya yıxılarsa və ya yanlış bir sahəyə işarə edərsə nə etməli? Əllə hərəkət edə bilməyimiz üçün bu kimi halları bildirmək üçün bir yola ehtiyacımız var idi.
Sensor məsafə oxunuşlarını təmin edə bilmirsə, sistem dəyişmiş vəziyyəti buluda göndərir və müvafiq bildiriş yaradır.
Məntiq aşağıdakı kodla göstərilmişdir.
məsafə = wait_for_distance () # Əgər məsafə yoxdursa, mövcud su dərinliyini oxuyun: log_error ('Məsafə xətası!') arxa plana bildir (calc_alert (SENSOR_ERROR)) göndər (bulud, dəyişənlər, məsafə, error_code = SENSOR_ERROR, güc = Doğru)
Sensor yerində olduqda saxlanmalı olan əməliyyat su səviyyəsi aralığımız var. Mövcud suyun səviyyəsinin bu aralığa düşüb düşmədiyini yoxlayırıq:
# Sensordan su səviyyəsinə qədər olan məsafə # qəhvə maşınının su anbarı əsasında MIN_DISTANCE = 2 # sm MAX_DISTANCE = 8 # sm
# Məsafə gözlənilən aralığın xaricindədir: tökməyə başlamayın
əgər məsafə> MAX_DISTANCE * 2: log_error ('Məsafə aralığın xaricindədir: %.2f' % məsafə) davam edin
Bir nasazlıq olduqda nasos aktiv olarsa onu söndürürük.
əgər is_pump_on () və prev_distance <STOP_PUMP_DISTANCE + DISTANCE_DELTA: log_error ('[!] Nasosun təcili dayanması. Məsafə sensorundan siqnal yoxdur')
toggle_pump (STOP_PUMP)
Şüşə su bitdikdə işi də emal edirik. Pompa işləyərkən suyun səviyyəsinin dəyişməyəcəyini yoxlayırıq. Əgər belədirsə, sistem 5 saniyə gözləyir və sonra nasosun sönüb -sönmədiyini yoxlayır. Əgər yoxdursa, sistem təcili nasosun bağlanmasını həyata keçirir və səhv bildirişi göndərir.
PUMP_STOP_TIMEOUT = 5 # secsemergency_stop_time = Yoxdur
def set_emergency_stop_time (indi, tökülür):
global Emergency_stop_time Emergency_stop_time = indi + başqa PUMP_STOP_TIMEOUT
def check_water_source_empty (indi):
Emergency_stop_time və indi> Emergency_stop_time qayıdın
# --------- əsas döngə -----------
əgər GPIO.event_detected (GPIO_PUMP): is_pouring = is_pump_on () set_emergency_stop_time (indi, tökülür) #…
qlobal nasos_aktiv
əgər check_water_source_empty (indi): log_error ('[!] Nasosun təcili dayandırılması. / Su mənbəyi boş') toggle_pump (STOP_PUMP) pump_disabled = Doğru
Yuxarıda, təcili dayanma zamanı yaranan bir mesaj qeydinin nümunəsidir.
Addım 4: Sistemin 24/7 işlədilməsi
Cihazdakı kod düzəldilir və problemsiz işləyir. Bir xidmət olaraq başladıq, buna görə Raspberry Pi yenidən başladıqda yenidən başlayacaq. Rahatlıq üçün, yerləşdirmə, xidmətin işlənməsi və qeydlərə baxmaqla kömək edən bir Makefile yaratdıq.
. PHONY: yükləmənin başlanğıc dayanma vəziyyət qeydini yerləşdirin MAIN_FILE: = qəhvə-nasosu/main.py SERVICE_INSTALL_SCRIPT: = service_install.sh SERVICE_NAME: = qəhvə-nasosu.xidməti
yüklemek:
chmod +x $ (SERVICE_INSTALL_SCRIPT) sudo./$(SERVICE_INSTALL_SCRIPT) $ (MAIN_FILE)
qaç:
sudo python3 $ (MAIN_FILE)
başlamaq:
sudo systemctl start $ (SERVICE_NAME)
status:
sudo systemctl status $ (SERVICE_NAME)
dayan:
sudo systemctl stop $ (SERVICE_NAME)
qeyd:
sudo journalctl -u qəhvə nasosu -bu gündən bəri
yerləşdirmək:
rsync -av qəhvə nasosu sensor qurğusu Makefile *.sh pi@XX. XX. XXX. XXX: ~/
Bu faylı və bütün lazımi skriptləri depomuzda tapa bilərsiniz.
Addım 5: Bulud Monitorinqi
Bir idarəetmə paneli tətbiq etmək üçün Cloud4RPi -dən istifadə etdik. Əvvəlcə sistemin əsas parametrlərini göstərmək üçün vidjetlər əlavə etdik.
Yeri gəlmişkən, STATUS dəyişəninin widgetı dəyərinə görə fərqli rəng sxemlərindən istifadə edə bilər (yuxarıdakı şəklə baxın).
Dinamik məlumatları göstərmək üçün bir diaqram vidceti əlavə etdik. Aşağıdakı şəkildə nasosun AÇMA və SÖKMƏ anını və müvafiq su səviyyələrini görə bilərsiniz.
Daha uzun bir müddət təhlil etsəniz, zirvələri görə bilərsiniz - nasos işləyərkən.
Cloud4RPi ayrıca fərqli hamarlaşdırma səviyyələrini təyin etməyə imkan verir.
Addım 6: İşləyir
İşləyir! İdarəetmə paneli bütövlükdə aşağıda göstərildiyi kimi görünür.
Hal -hazırda avtomatik nasosumuz bir neçə həftədir işləyir və su şüşələrini dəyişdirməyimiz lazım idi. Layihəmizin tam kodu GitHub depomuzda mövcuddur.