Browse Source

- added support for using Tasmota ESP8266 firmware as a Serial Bridge for building an MQTT-CUL rather than my own outdated, instable and never published MQTT-Serial-firmware
tested with Tasmota v9.3.1

FloKra 1 year ago
parent
commit
f7ef16dc08
5 changed files with 104 additions and 7 deletions
  1. 4 0
      CHANGELOG.txt
  2. 2 1
      README.md
  3. 74 0
      Tasmota_Serial-MQTT-Bridge_for_MQTT-CUL.md
  4. 8 2
      src/cul2mqtt.ini
  5. 16 4
      src/cul2mqtt.py

+ 4 - 0
CHANGELOG.txt

@@ -1,3 +1,7 @@
+2021-03-14:
+  - added support for using Tasmota ESP8266 firmware as a Serial Bridge for building an MQTT-CUL rather than my own outdated, instable and never published MQTT-Serial-firmware
+    tested with Tasmota v9.3.1
+
 2020-12-09:
   - fixed bug: program terminated when UART-CUL enabled/configured but not available
   - fix bug in MQTT input when using 'add_statTopics_on'

+ 2 - 1
README.md

@@ -15,7 +15,8 @@ Features:
 - supports InterTechno compatible learning code protocols, i.E. EV1527 based remotes (receiving, sending and automatic TX code generation supported)
 - basic support for other 433 MHz RF remotes - including many self learning models (for receiving only)
 - developed for use with CUL transceivers with firmware **[a-culfw](https://github.com/heliflieger/a-culfw)**
-- supports 2 CUL transceivers concurrently - one connected directly via UART, and another one via MQTT-UART-Bridge (link to my project to be posted), in order to improve site coverage and reliability, where preferred TX interface can be defined per device
+- supports 2 CUL transceivers concurrently - one connected directly via UART, and another one via MQTT-UART-Bridge using an ESP8266 device running the great Tasmota firmware, in order to improve site coverage and reliability, where preferred TX interface can be defined per device
+  More info on Tasmota as an MQTT-Serial-Bridge: [Tasmota Serial-MQTT-Bridge for MQTT-CUL](Tasmota_Serial-MQTT-Bridge_for_MQTT-CUL.md)
 - intended for running on a Raspberry Pi or similar
 - devices configuration using YAML file, base configuration using INI file
 

+ 74 - 0
Tasmota_Serial-MQTT-Bridge_for_MQTT-CUL.md

@@ -0,0 +1,74 @@
+Tasmota Serial (MQTT) Bridge for MQTT-CUL
+==========================================
+
+
+
+## Hardware
+
+- Wemos D1 mini or equivalent ESP8266 board running Tasmota (tested with v9.3.1)
+- DIY-CUL device (Arduino Pro Mini with aCULfw + C1101 Transceiver)
+  - RX/TX connected to Wemos D1 mini hardware UART (TX->RX and vice versa) using level shifters
+
+
+
+## Tasmota-Configuration
+
+##### Set baudrate for Hardware-UART
+
+CUL-Device uses 38400 bps
+
+```
+baudrate 38400
+```
+
+
+
+##### Set serial delimiter
+
+```
+serialdelimiter 128
+```
+
+- CUL finishes every message with CR+LF (*\r\n*)
+- *serialdelimiter 128* filters all unprintable chars and seems to take both CR and LF as a delimiter - at least both are filtered out and consequent messages are not concatenated, which happens if using NO serialdelimiter (value set to >128)
+
+
+
+##### Set serial config
+
+```
+SerialConfig 8N1
+```
+
+
+
+##### Initialize CUL on Tasmota startup
+
+Additionally, Tasmota´s Serial bridge is only active after the *SerialSend* function was used once after startup.
+
+In my setup I need to get also "RAW" data from CUL, as I am using remote controls not directly supported by the aCULfw firmware, so I use the X05 command. If this is not needed, the right command is likely to be X21. 
+For details see: http://culfw.de/commandref.html 
+
+```
+rule1 on system#boot do serialsend X05\r\n endon
+```
+
+activate the rule:
+
+```
+rule1 1
+```
+
+
+
+##### Additional rule for publishing SerialReceived output on another topic
+
+```
+rule2 on SerialReceived#Data do publish MQTTCUL/received %value% endon
+```
+
+- Unfortunately this rule will only work if ther is NO control char in the received string, so it is mandatory to use a *SerialDelimiter* setting that filters out all of them (i.E. SerialDelimiter 128 does the job). 
+- The output of this rule is ALWAYS UPPERCASE. Don´t know why, but that´s how Tasmota handles it. Regarding CUL output this could be a problem, as it outputs lowercase chars in most messages. 
+  - **CUL2MQTT.py** handles this by putting all data received from MQTT-CUL topic to lowercase (as all of the logic has already been completed and was written based on the normal lowercase output seen on any CUL device). 
+  - **CUL2MQTT.py** now also supports the Tasmota ***tele/TOPIC/RESULT*** output in JSON format directly. It is preferred to use it this way, without the additional rule. 
+

+ 8 - 2
src/cul2mqtt.ini

@@ -24,8 +24,14 @@ culInitCmd = X05
 culSendsRSSI = False
 receive_from_mqtt_cul = True
 send_on_mqtt_cul = True
-mqtt_cul_topic_received = MQTTCUL/received
-mqtt_cul_topic_send = MQTTCUL/send
+
+# for "classic" MQTT-CUL
+#mqtt_cul_topic_received = MQTTCUL/received
+#mqtt_cul_topic_send = MQTTCUL/send
+
+# for Tasmota based MQTT-CUL using Tasmota´s serial bridge functions
+mqtt_cul_topic_received = tele/Tasmota-MQTT-CUL/RESULT
+mqtt_cul_topic_send = cmnd/Tasmota-MQTT-CUL/SerialSend
 
 [mqtt]
 server = mqtt.lan

+ 16 - 4
src/cul2mqtt.py

@@ -302,15 +302,27 @@ def on_message(client, userdata, msg):
     payload = msg.payload.decode("utf-8")
     
     if verbose:
+        log_write("")
         log_write("MQTT received: " + msg.topic + " -> " + str(payload))
     
     # MQTT message is output from CUL
     if receive_from_mqtt_cul and msg.topic == mqtt_cul_topic_received:
         payload = payload.rstrip()
-        if verbose:
-            log_write("")
-            log_write("MQTT-CUL RX: '" + payload + "'")
-        cul_received(payload, "MQTT")
+            
+        # support output from Tasmota SerialBridge on tele/[DEVICE]/RESULT topic
+        # example: {"SerialReceived":"p10  144   80  480   48   32 1360  28  1  3 4   160  6336     0 735C1470"}
+        if payload.startswith('{"SerialReceived":'):
+            payload_json = json.loads(payload)
+            payload = payload_json.get('SerialReceived')
+            if payload != None:
+                cul_received(payload, "MQTT") # to lower case as MQTT CUL via Tasmota SerialBridge with Rule changes output to all uppercase
+                if verbose:
+                    log_write("MQTT-CUL RX: '" + payload + "'")
+        elif not payload.startswith('{'):
+            # ignore everything different starting with { 
+            cul_received(payload.lower(), "MQTT") # to lower case as MQTT CUL via Tasmota SerialBridge with Rule changes output to all uppercase
+            if verbose:
+                log_write("MQTT-CUL RX: '" + payload.lower() + "'")
         
     else:
         for in_topic, dev in InTopicsToDevIds.items():