Modifying MQTT device behaviour via automation

Hi all,

TL;DR
Want to modify MQTT device behaviour, more specifically On/Off button onXiaomi ZNCZ04LM`. Have a somewhat working config with automation but it’s complaining about value_template not being set. I just want to pass it as a string instead of as a variable.

specifications:

  • ESXi 6.7u3;
  • HPE Microserver G8;
  • Debian 10 VM;
  • 2 cores;
  • 3gb RAM.

Used software:

  • Home Assistant supervised;
  • Core-2021.9.7;
  • Zigbee2mqtt (1.21.2-1) Add-on;
  • Mosquitto broker (5.1) Add-on.

I have added MQTT via configuration.yaml, snippet below:

mqtt:
  broker: core-mosquitto
  discovery: true
  client_id: 'HASSIO-INTEGRATION'
  username: !secret mqtt_username
  password: !secret mqtt_password

Configuration file of Zigbee2MQTT is not neccessary but if one needs it i can always supply it.

Where did the problem originate from:
I have multiple Xiaomi ZNCZ04LM smart wall plugs that i use to monitor powerusage of my servers. The problem is, the server providing MQTT and Zigbee are also switched via those smart wall plugs. In the past i’ve had it happen that i accidentally switched off the power to the machine hosting most of my VM’s rendering most of my service(s) inoperable as i then have no possibility to power it up again.

What i’ve researched to remedy my issue:
So i’ve looked into disabling auto-discovery for every sensor and manually creating entries in my configuration.yaml but did not succeed in this. I then tried to look into modifying the published topics of my MQTT server to modify behaviour. My reasoning was, since i can not modify behaviour before publishing devices, i shall try to modify behaviour after publishing devices.I found a topic (no link unfortunately) that described how one could create an automation that publishes something to a topic.

What i currently have functioning:
I currently have an automation that is triggered by the start of home assistant, listens to a certain topic (the config of 1 switch) and then has an action that publishes a different payload with the modified values to that same topic:

alias: Republish topic to Xiaomi_Mijja_Wallsocket2
description: >-
  This experimental way of disabling the button on the Xiaomi Mijia Wallsocket
  is done by publishing a empty payload to the topic, followed by the right
  payload to the topic.
trigger:
  - event: start
    platform: homeassistant
  - payload: >-
      {"payload_off":"OFF","payload_on":"ON","value_template":"{{value_json.state}}","command_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2/set","state_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","json_attributes_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","name":"Xiaomi_Mijja_Wallsocket2_switch","unique_id":"0x04cf8cdf3c7b1e56_switch_zigbee2mqtt","device":{"identifiers":["zigbee2mqtt_0x04cf8cdf3c7b1e56"],"name":"Xiaomi_Mijja_Wallsocket2","sw_version":"Zigbee2MQTT
      1.21.2","model":"Mi power plug ZigBee EU
      (ZNCZ04LM)","manufacturer":"Xiaomi"},"availability_topic":"zigbee2mqtt/bridge/state"}
    platform: mqtt
    topic: homeassistant/switch/0x04cf8cdf3c7b1e56/switch/config
condition: []
action:
  - data:
      payload: >-
        {"payload_off":"ON", "payload_on":"ON",
        "value_template":"{{'{{value_json.state}}'}}","command_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2/set","state_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","json_attributes_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","name":"Xiaomi_Mijja_Wallsocket2_switch","unique_id":"0x04cf8cdf3c7b1e56_switch_zigbee2mqtt","device":{"identifiers":["zigbee2mqtt_0x04cf8cdf3c7b1e56"],"name":"Xiaomi_Mijja_Wallsocket2","sw_version":"Zigbee2MQTT
        1.21.2","model":"Mi power plug ZigBee
        EU(ZNCZ04LM)","manufacturer":"Xiaomi"},"availability_topic":"zigbee2mqtt/bridge/state"}
      qos: 2
      retain: true
      topic: homeassistant/switch/0x04cf8cdf3c7b1e56/switch/config
    service: mqtt.publish
  - data:
      message: >-
        Modified payload has been sent to Xiaomi_Mijja_Wallsocket2
        (Workstation).
      notification_id: MQTTMESSAGE2
      title: Notice!
    service: persistent_notification.create
mode: single

Behaviour is verified via MQTT Explorer, as i see the values for payload_off changes to "ON" which basically eliminates the possibility to accidentally power down the wall plug via software. Physical button still works but there is no accidentally pushing in that button :slight_smile:.

I always had warnings/errors in the logs of Home Assistant Core, but starting from Core-2021.10 those warnings will be breaking. The error i’m getting is:

021-10-08 18:34:58 ERROR (MainThread) [homeassistant.helpers.template] Template variable error: 'value_json' is undefined when rendering '{"payload_off":"OFF","payload_on":"ON","value_template":"{{value_json.state}}","command_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2/set","state_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","json_attributes_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","name":"Xiaomi_Mijja_Wallsocket2_switch","unique_id":"0x04cf8cdf3c7b1e56_switch_zigbee2mqtt","device":{"identifiers":["zigbee2mqtt_0x04cf8cdf3c7b1e56"],"name":"Xiaomi_Mijja_Wallsocket2","sw_version":"Zigbee2MQTT 1.21.2","model":"Mi power plug ZigBee EU (ZNCZ04LM)","manufacturer":"Xiaomi"},"availability_topic":"zigbee2mqtt/bridge/state"}'
2021-10-08 18:34:58 ERROR (MainThread) [homeassistant.components.automation.republish_topic_to_xiaomi_mijja_wallsocket2_duplicate] Got error 'UndefinedError: 'value_json' is undefined' when setting up triggers for Republish topic to Xiaomi_Mijja_Wallsocket2 (Duplicate)

So i understand that the reason why i get this error is because value_json is undefined. And that is true, because it is published to a topic on MQTT. I tried surrounding it with another set of {{}} as i’ve read that that might let HA know that it should not be treated as a variable but just as a string. I also tried surrounding it by single quotes but that wasn’t helpfull either.

I’ve also read that you can do {{value.json | null}} or similar but the docs weren’t helpful.

I am however unable to fix the error im getting. I don’t know what to do to fix this, so would like to have some guidance here. Also don’t know if this is the best solution for the problem, but hey it works.

try

alias: Republish topic to Xiaomi_Mijja_Wallsocket2
description: >-
  This experimental way of disabling the button on the Xiaomi Mijia Wallsocket
  is done by publishing a empty payload to the topic, followed by the right
  payload to the topic.
trigger:
  - event: start
    platform: homeassistant
  - payload: >-
      {"payload_off":"OFF","payload_on":"ON","value_template":"{{value_json.state}}","command_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2/set","state_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","json_attributes_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","name":"Xiaomi_Mijja_Wallsocket2_switch","unique_id":"0x04cf8cdf3c7b1e56_switch_zigbee2mqtt","device":{"identifiers":["zigbee2mqtt_0x04cf8cdf3c7b1e56"],"name":"Xiaomi_Mijja_Wallsocket2","sw_version":"Zigbee2MQTT
      1.21.2","model":"Mi power plug ZigBee EU
      (ZNCZ04LM)","manufacturer":"Xiaomi"},"availability_topic":"zigbee2mqtt/bridge/state"}
    platform: mqtt
    topic: homeassistant/switch/0x04cf8cdf3c7b1e56/switch/config
condition: []
action:
  - data:
      payload: >-
        {"payload_off":"ON", "payload_on":"ON",
        "value_template":{% raw %}"{{value_json.state}}"{% endraw %},"command_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2/set","state_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","json_attributes_topic":"zigbee2mqtt/Xiaomi_Mijja_Wallsocket2","name":"Xiaomi_Mijja_Wallsocket2_switch","unique_id":"0x04cf8cdf3c7b1e56_switch_zigbee2mqtt","device":{"identifiers":["zigbee2mqtt_0x04cf8cdf3c7b1e56"],"name":"Xiaomi_Mijja_Wallsocket2","sw_version":"Zigbee2MQTT
        1.21.2","model":"Mi power plug ZigBee
        EU(ZNCZ04LM)","manufacturer":"Xiaomi"},"availability_topic":"zigbee2mqtt/bridge/state"}
      qos: 2
      retain: true
      topic: homeassistant/switch/0x04cf8cdf3c7b1e56/switch/config
    service: mqtt.publish
  - data:
      message: >-
        Modified payload has been sent to Xiaomi_Mijja_Wallsocket2
        (Workstation).
      notification_id: MQTTMESSAGE2
      title: Notice!
    service: persistent_notification.create
mode: single

2 Likes

This seemed to do the trick! Had to do the same in trigger as that was als complaining. The docs on Templating didn’t mention anything about {% raw %} but looking up the syntax of Jinja2 templates gave some valuable information. Thanks!

Do you think however that this is the best way to do it though? Because now every time i update Zigbee2MQTT add-on i need to modify my automations as well. Luckily i only have three wall plugs that need this modification but what if i had twenty? I could maybe use variables passed in (or requested) to replace the currently static values.

The discovery messages Zigbee2mqtt sends don’t change normally between releases, except the last few releases for devices that measure power, due to changes in HA. Let’s hope things settle down at that front. I’m tired of changing my discovery scripts too for the last HA releases.