second commit

This commit is contained in:
denis
2026-03-10 13:10:32 +01:00
parent b5cc0106c6
commit 3aac7ff9b9
101 changed files with 22046 additions and 1 deletions
+180
View File
@@ -0,0 +1,180 @@
'''
Devices
Created on 23 août 2022
@author: denis@e-educ.fr
Flow and Frequency output of the YF-S201
Flow(L/H) Frequency(Hz)
120 16
240 32.5
360 49.3
480 65.5
600 82
720 90.2
F = 7.5 Q Q: l/mn
'''
import logging, threading, random
from modules import sensors as dev, utils, gpiolib as gpio
logger = logging.getLogger(__name__)
logging.basicConfig(level=logging.INFO)
class YF_S201(dev.InputDevice):
waterflow_timeout = 2
pulse_counter = 0
start_counter = False
stop_counter = None
def __init__(self, pin, register=None, publish=None):
super().__init__(pin, register=register, callback=self.on_count_pulse, pull_up_down=gpio.IO_PULL_UP,)
self.publish = publish
threading.Thread(target=self.waterflow_process, args=()).start()
def waterflow_publish(self, flow=None):
if self.publish is not None:
self.publish(dict(
uuid=self.key,
topic="waterflow",
ts=utils.ts_now(),
flow=flow,
)
)
def on_count_pulse(self, channel):
if self.start_counter:
self.pulse_counter += 1
def wait_for_counts(self, timeout):
self.pulse_counter = 0
self.start_counter = True
threading.Event().wait(timeout)
self.start_counter = False
def waterflow_process(self):
self.stop_counter = threading.Event()
while not self.stop_counter.is_set():
self.wait_for_counts(self.waterflow_timeout)
flow = self.pulse_counter / 7.5
if flow:
logger.info(f'\nwaterflow_process flow = {flow}')
self.waterflow_publish(flow)
def stop(self):
self.stop_counter.set()
class Relay(dev.RelayFromShiftOut):
def __init__(self, shift_out_register, register=None, publish=None):
super().__init__(shift_out_register, register, relay_timeout=1.0)
self.publish = publish
self.start_time, self.end_time = 0, 0
self.started = False
self.duration_timer = threading.Event()
self.water_flow_timer = threading.Event()
self.flow, self.rate = 0.00, 0.00
self.flow_meter_start()
self.relay_publish('init', index=self.index, label=self.label, dev_type=self.dev_type)
def now(self):
return utils.ts_now_s()
def relay_publish(self, topic, **kwargs):
if self.publish is not None:
self.publish(topic, **dict(
uuid=self.key,
ts=utils.ts_now_s(),
relay_state=self.is_on(),
elapsed=self.time_elapsed(),
remaining=self.time_remaining(),
flow=self.flow,
rate=self.rate,
**kwargs
)
)
def time_elapsed(self):
elapsed = self.now() - self.start_time
if self.start_time <= 0 or elapsed <= 0:
elapsed = 0
return elapsed
def time_remaining(self):
remaining = self.end_time - self.now()
if remaining < 0:
remaining = 0
return remaining
def is_it_over(self, timeout):
elapsed = self.now() - self.start_time
if elapsed > timeout:
self.duration_timer.set()
def _open(self, timeout):
self.duration_timer = threading.Event()
self.started = True
while not self.duration_timer.is_set():
try:
if self.started:
self.is_it_over(timeout)
threading.Event().wait(1.0)
except Exception as e:
logger.error(f'run error {e}')
self.start_time = 0
self.relay_stop()
def relay_start(self, duration=0):
self.start_time = self.now()
self.end_time = self.start_time + duration
self.open()
if duration > 0:
threading.Thread(target=self._open, args=(duration, )).start()
self.rate, self.flow = 0.00, 0.00
self.begin = self.now()
self.water_flow_timer.set()
self.relay_publish('start')
def relay_stop(self):
self.duration_timer.set()
self.close()
self.started = False
self.water_flow_timer.clear()
self.relay_publish('stop')
def relay_halt(self):
if self.is_on():
self.started = False
def relay_restart(self):
if self.is_on():
self.started = True
def relay_status(self):
self.relay_publish('status')
def _flow_meter(self):
while True:
try:
self.water_flow_timer.wait()
elapsed = (self.now() - self.begin)/60
self.flow = random.randint(1050, 1065)/100 * elapsed
self.rate = self.flow / elapsed if elapsed > 0 else 0.00
threading.Event().wait(1.0)
except Exception as e:
logger.error(f'flow_meter_process error {e}')
threading.Event().wait(1.0)
def flow_meter_start(self):
self.begin = self.now()
threading.Thread(target=self._flow_meter).start()