|
@@ -8,34 +8,7 @@ import paho.mqtt.client as mqtt
|
|
import json
|
|
import json
|
|
|
|
|
|
# --- CONFIGURATION ---
|
|
# --- CONFIGURATION ---
|
|
-
|
|
|
|
-# timeout in s to end script when nothing is received (will be restarted by systemd then)
|
|
|
|
-# must be higher than getStatusInterval
|
|
|
|
-quitOnNoReceiveTimeout = 75
|
|
|
|
-
|
|
|
|
-# status file - on ramdrive (/tmp on RasPi by default)
|
|
|
|
-# is "touched" every time a serial message comes in so that working communication can be monitored easily
|
|
|
|
-statusFile = '/tmp/ioext_running'
|
|
|
|
-
|
|
|
|
-# serial port config
|
|
|
|
-serialPort = '/dev/serial/by-id/usb-1a86_USB_Serial-if00-port0'
|
|
|
|
-serialBaud = 57600
|
|
|
|
-serialTimeout = 1 # should be 1 as above interval/timeout relies on it
|
|
|
|
-
|
|
|
|
-# MQTT config
|
|
|
|
-mqtt_server = "mqtt.lan"
|
|
|
|
-mqtt_port = 1883
|
|
|
|
-mqtt_user = "user"
|
|
|
|
-mqtt_password = "password"
|
|
|
|
-
|
|
|
|
-mqtt_base_topic = "T5/HomeSvrIOExt"
|
|
|
|
-
|
|
|
|
-mqtt_topic_tuerkontakt = "T5/Wohnungstuer/Tuerkontakt"
|
|
|
|
-mqtt_topic_pir1 = "T5/VZ/PIR1"
|
|
|
|
-mqtt_topic_pir2 = "T5/VZ/PIR2"
|
|
|
|
-mqtt_topic_out_temp = "T5/Abstr/Sensors/temp"
|
|
|
|
-mqtt_topic_out_hum = "T5/Abstr/Sensors/hum"
|
|
|
|
-
|
|
|
|
|
|
+import config
|
|
# --- END CONFIGURATION ---
|
|
# --- END CONFIGURATION ---
|
|
|
|
|
|
|
|
|
|
@@ -47,13 +20,12 @@ verbose = False
|
|
debug = False
|
|
debug = False
|
|
quiet = True
|
|
quiet = True
|
|
|
|
|
|
-
|
|
|
|
lastState_tk = None
|
|
lastState_tk = None
|
|
lastState_pir1 = None
|
|
lastState_pir1 = None
|
|
lastState_pir2 = None
|
|
lastState_pir2 = None
|
|
-
|
|
|
|
# --- END GLOBAL VARS ---
|
|
# --- END GLOBAL VARS ---
|
|
|
|
|
|
|
|
+
|
|
if len(sys.argv) >= 2:
|
|
if len(sys.argv) >= 2:
|
|
if sys.argv[1] == "-q":
|
|
if sys.argv[1] == "-q":
|
|
verbose = False
|
|
verbose = False
|
|
@@ -97,25 +69,27 @@ mqttc.on_connect = on_connect
|
|
#mqttc.on_disconnect = on_disconnect
|
|
#mqttc.on_disconnect = on_disconnect
|
|
#mqttc.on_message = on_message
|
|
#mqttc.on_message = on_message
|
|
|
|
|
|
-mqttc.username_pw_set(mqtt_user, mqtt_password)
|
|
|
|
-mqttc.connect(mqtt_server, mqtt_port, 60)
|
|
|
|
|
|
+mqttc.username_pw_set(config.mqtt_user, config.mqtt_password)
|
|
|
|
+mqttc.connect(config.mqtt_server, config.mqtt_port, 60)
|
|
|
|
|
|
mqttc.loop_start()
|
|
mqttc.loop_start()
|
|
|
|
|
|
-ser = serial.Serial(port=serialPort,
|
|
|
|
- baudrate = serialBaud,
|
|
|
|
|
|
+ser = serial.Serial(port=config.serialPort,
|
|
|
|
+ baudrate = config.serialBaud,
|
|
parity=serial.PARITY_NONE,
|
|
parity=serial.PARITY_NONE,
|
|
stopbits=serial.STOPBITS_ONE,
|
|
stopbits=serial.STOPBITS_ONE,
|
|
bytesize=serial.EIGHTBITS,
|
|
bytesize=serial.EIGHTBITS,
|
|
- timeout=serialTimeout)
|
|
|
|
|
|
+ timeout=config.serialTimeout)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
try:
|
|
try:
|
|
while True:
|
|
while True:
|
|
##ser.flushInput() ## attention truncates incoming strings if there is little time between them
|
|
##ser.flushInput() ## attention truncates incoming strings if there is little time between them
|
|
|
|
+
|
|
#read buffer until cr/lf
|
|
#read buffer until cr/lf
|
|
serLine = ser.readline().strip()
|
|
serLine = ser.readline().strip()
|
|
|
|
+
|
|
# catch exception on invalid char coming in: UnicodeDecodeError: 'ascii' codec can't decode byte 0xf4 in position 6: ordinal not in range(128)
|
|
# catch exception on invalid char coming in: UnicodeDecodeError: 'ascii' codec can't decode byte 0xf4 in position 6: ordinal not in range(128)
|
|
try:
|
|
try:
|
|
serLine = serLine.decode('ascii')
|
|
serLine = serLine.decode('ascii')
|
|
@@ -125,13 +99,27 @@ try:
|
|
# if there came something in...
|
|
# if there came something in...
|
|
if(serLine):
|
|
if(serLine):
|
|
noReceiveCount = 0
|
|
noReceiveCount = 0
|
|
- touch(statusFile)
|
|
|
|
- #serLine = serLine.strip('\'')
|
|
|
|
- #serLine = serLine.strip('\r')
|
|
|
|
- #serLine = serLine.strip('\n')
|
|
|
|
|
|
+
|
|
|
|
+ # touch status file if configured
|
|
|
|
+ try:
|
|
|
|
+ config.statusFile
|
|
|
|
+ except:
|
|
|
|
+ if debug:
|
|
|
|
+ print("statusFile not defined")
|
|
|
|
+ else:
|
|
|
|
+ if config.statusFile is not None and config.statusFile != "":
|
|
|
|
+ try:
|
|
|
|
+ touch(config.statusFile)
|
|
|
|
+ except:
|
|
|
|
+ if debug:
|
|
|
|
+ print("ERROR - could not touch statusFile '" + str(config.statusFile) + "'")
|
|
|
|
+ else:
|
|
|
|
+ if debug:
|
|
|
|
+ print("statusFile not configured")
|
|
|
|
+
|
|
if verbose:
|
|
if verbose:
|
|
print ('RX: ' + repr(serLine)) #Echo the serial buffer bytes up to the CRLF back to screen
|
|
print ('RX: ' + repr(serLine)) #Echo the serial buffer bytes up to the CRLF back to screen
|
|
- mqttc.publish(mqtt_base_topic + "/RX", str(serLine), qos=0, retain=False)
|
|
|
|
|
|
+ mqttc.publish(config.mqtt_base_topic + "/RX", str(serLine), qos=0, retain=False)
|
|
|
|
|
|
# Tuerkontakt
|
|
# Tuerkontakt
|
|
if serLine.startswith('P2='):
|
|
if serLine.startswith('P2='):
|
|
@@ -143,7 +131,7 @@ try:
|
|
|
|
|
|
if newState is not None and lastState_tk != newState:
|
|
if newState is not None and lastState_tk != newState:
|
|
lastState_tk = newState
|
|
lastState_tk = newState
|
|
- mqttc.publish(mqtt_topic_tuerkontakt, newState, qos=0, retain=False)
|
|
|
|
|
|
+ mqttc.publish(config.mqtt_topic_tuerkontakt, newState, qos=0, retain=False)
|
|
|
|
|
|
# PIR #1
|
|
# PIR #1
|
|
if serLine.startswith('P3='):
|
|
if serLine.startswith('P3='):
|
|
@@ -155,7 +143,7 @@ try:
|
|
|
|
|
|
if newState is not None and lastState_pir1 != newState:
|
|
if newState is not None and lastState_pir1 != newState:
|
|
lastState_pir1 = newState
|
|
lastState_pir1 = newState
|
|
- mqttc.publish(mqtt_topic_pir1, newState, qos=0, retain=False)
|
|
|
|
|
|
+ mqttc.publish(config.mqtt_topic_pir1, newState, qos=0, retain=False)
|
|
|
|
|
|
# PIR #2
|
|
# PIR #2
|
|
if serLine.startswith('P4='):
|
|
if serLine.startswith('P4='):
|
|
@@ -167,7 +155,7 @@ try:
|
|
|
|
|
|
if newState is not None and lastState_pir2 != newState:
|
|
if newState is not None and lastState_pir2 != newState:
|
|
lastState_pir2 = newState
|
|
lastState_pir2 = newState
|
|
- mqttc.publish(mqtt_topic_pir2, newState, qos=0, retain=False)
|
|
|
|
|
|
+ mqttc.publish(config.mqtt_topic_pir2, newState, qos=0, retain=False)
|
|
|
|
|
|
# DHT TH sensor
|
|
# DHT TH sensor
|
|
# {"T":26.60,"H":36}
|
|
# {"T":26.60,"H":36}
|
|
@@ -176,22 +164,10 @@ try:
|
|
t = round(float(th["T"]), 1)
|
|
t = round(float(th["T"]), 1)
|
|
h = int(th["H"])
|
|
h = int(th["H"])
|
|
if t >= -20 and t <= 50:
|
|
if t >= -20 and t <= 50:
|
|
- mqttc.publish(mqtt_topic_out_temp, str(t), qos=0, retain=False)
|
|
|
|
|
|
+ mqttc.publish(config.mqtt_topic_out_temp, str(t), qos=0, retain=False)
|
|
if h >= 0 and h <= 100:
|
|
if h >= 0 and h <= 100:
|
|
- mqttc.publish(mqtt_topic_out_hum, str(h), qos=0, retain=False)
|
|
|
|
|
|
+ mqttc.publish(config.mqtt_topic_out_hum, str(h), qos=0, retain=False)
|
|
|
|
|
|
-
|
|
|
|
- ## publish MQTT messages
|
|
|
|
- #if serLine.startswith('EVENT_'):
|
|
|
|
- # mqttc.publish(mqtt_topic_event, serLine, qos=0, retain=False)
|
|
|
|
- # #os.system(os.path.dirname(os.path.realpath(__file__))+'/event_top5_klingel.py')
|
|
|
|
- #
|
|
|
|
- #elif serLine.startswith('OK'):
|
|
|
|
- # mqttc.publish(mqtt_topic_cmdresponse, serLine, qos=0, retain=False)
|
|
|
|
- #
|
|
|
|
- #elif serLine.startswith('{"'):
|
|
|
|
- # mqttc.publish(mqtt_topic_cmdresponse, serLine, qos=0, retain=False)
|
|
|
|
- # #os.system(os.path.dirname(os.path.realpath(__file__))+'/event_top5_klingel.py')
|
|
|
|
|
|
|
|
# nothing came in this time...
|
|
# nothing came in this time...
|
|
else:
|
|
else:
|
|
@@ -200,19 +176,8 @@ try:
|
|
print("noReceiveCount=" + str(noReceiveCount))
|
|
print("noReceiveCount=" + str(noReceiveCount))
|
|
|
|
|
|
# quit script if nothing has been received for some time - will be restarted by systemd
|
|
# quit script if nothing has been received for some time - will be restarted by systemd
|
|
- if noReceiveCount >= quitOnNoReceiveTimeout:
|
|
|
|
|
|
+ if noReceiveCount >= config.quitOnNoReceiveTimeout:
|
|
quit()
|
|
quit()
|
|
|
|
|
|
-
|
|
|
|
- ## get status every [getStatusInterval] seconds
|
|
|
|
- #getStatusCount += 1
|
|
|
|
- #if getStatusCount >= getStatusInterval:
|
|
|
|
- # getStatusCount = 0
|
|
|
|
- # serCmd = 'status\n'
|
|
|
|
- # ser.write(serCmd.encode('ascii'))
|
|
|
|
- #if debug:
|
|
|
|
- # print("getStatusCount=" + str(getStatusCount))
|
|
|
|
-
|
|
|
|
-
|
|
|
|
except KeyboardInterrupt:
|
|
except KeyboardInterrupt:
|
|
print('\n')
|
|
print('\n')
|