Files
bt-mqtt-gateway/workers/msgw.py
T
2020-12-28 22:45:53 +01:00

87 lines
3.6 KiB
Python

from mqtt import MqttMessage
from workers.base import BaseWorker
import logger
import traceback
import time
REQUIREMENTS = ['pyserial']
_LOGGER = logger.get(__name__)
class MsgwWorker(BaseWorker):
LOGNAME = "mysensors-nrf24"
def _setup(self):
_LOGGER.debug("Setting up " + self.LOGNAME)
import serial
self.ser = serial.Serial(self.port, self.baudrate, timeout=10)
if not hasattr(self, 'encoding'):
self.encoding = 'utf-8'
if not hasattr(self, 'timezone'):
self.timezone = 1
def config(self):
return []
def run(self, mqtt):
_LOGGER.debug("Starting " + self.LOGNAME + " at: %s" % self.ser.name)
while True:
try:
line = self.ser.readline()
if not line:
continue
_LOGGER.debug(self.LOGNAME + ": Serial.read: %s" % line)
splited_line = line.decode(self.encoding).strip().split(';', 5)
if len(splited_line) < 5:
raise Exception("protocol error: too few values")
# node-id ; child-sensor-id ; command ; ack ; type ; payload
#nodeid = int(splited_line[0])
#childid = int(splited_line[1])
command = int(splited_line[2])
#ack = int(splited_line[3])
ctype = int(splited_line[4])
payload = splited_line[5] if len(splited_line) > 5 else ''
topic = self.format_topic(*splited_line[0:5])
# Internal
if command == 3:
# I_TIME
if ctype == 1:
tm = time.localtime()
offset = self.timezone
if tm.tm_isdst == 1:
offset += 1
timevalue = str(offset*60*60+int(time.mktime(tm)))
resp = str.encode(splited_line[0]+";"+splited_line[1]+";3;0;1;"+timevalue+"\n")
self.ser.write(resp)
_LOGGER.error(self.LOGNAME + ": time request received, sending back %s" % resp)
continue
# I_CONFIG
elif ctype == 6:
resp = str.encode(splited_line[0]+";"+splited_line[1]+";3;0;6;M\n")
self.ser.write(resp)
_LOGGER.error(self.LOGNAME + ": config request received, sending back %s" % resp)
continue
mqtt.publish([MqttMessage(topic=topic, payload=payload)])
except Exception as e:
_LOGGER.error(self.LOGNAME + ": Caught exception in MsgwWorker.run(): {}".format(e))
traceback.print_exc();
except serial.serialutil.SerialException as e:
_LOGGER.error(self.LOGNAME + ": Caught exception in MsgwWorker.run(): {}".format(e))
traceback.print_exc();
self.ser = serial.Serial(self.port, self.baudrate, timeout=10)
def on_command(self, topic, value):
_LOGGER.debug(self.LOGNAME + ": on_command({}, {})".format(topic, value))
try:
splited_topic = topic.split('/')
line = str.encode(splited_topic[-5]+";"+splited_topic[-4]+";"+splited_topic[-3]+";"+splited_topic[-2]+";"+splited_topic[-1]+";")+value+b'\n'
_LOGGER.debug(self.LOGNAME + ": Serial.write: %s" % line)
self.ser.write(line)
except Exception as e:
_LOGGER.error(self.LOGNAME + ": Caught exception in MsgwWorker.on_command(): {}".format(e))
traceback.print_exc()
return []