Select entity based on a JSON value

I’ve been scratching my head over this all day! I’m trying to integrate a few RF switches via OpenMQTTGateway to control some lights. The simplest way I can think of for this is to create an automation with a message on my OMG topic as the trigger, and a template specifying which light to toggle depending on which switch I press.

Here is a sample of the output from OMG. It’s just standard JSON: {"value":12540546,"protocol":1,"length":24,"delay":287}

The unique identifier is the “value” string.

I created a sample automation with one switch below, this works fine

trigger:
  - platform: mqtt
    topic: "/home/OpenMQTTGateway/433toMQTT"
condition:
  - condition: template
    value_template: "{{ trigger.payload_json['value'] == 12540546 }}"
action:
  - service: light.toggle
  - entity_id: light.lounge_tv

What I want to do however is add in multiple of these, but I cannot for the life of me find a template that will work at all. This is the current form:

trigger:
  - platform: mqtt
    topic: "/home/OpenMQTTGateway/433toMQTT"
action:
  - service: light.toggle
    data_template:
      entity_id: >
          {% if is_state_attr('trigger.payload_json', 'value', '11073208') %}
            light.master_bedroom
          {% elif is_state_attr('trigger.payload_json', 'value', '12540548') %}
            light.lounge_tv
          {% elif is_state_attr('trigger.payload_json', 'value', '3735524') %}
            light.hallway_light
          {% endif %}

This does absolutely nothing. Neither do any of the following conditional templates I’ve tried:

{% if is_state('trigger.payload_json['value'], 'xxxxxxxx') %}
{% if is_state('trigger.payload_json.value', 'xxxxxxxx') %}
{% if 'trigger.payload_json['value'] == 'xxxxxxxx' %}
{% if 'trigger.payload_json.value' == 'xxxxxxxx' %}

Although the MQTT packet is received fine, it can’t seem to parse the JSON correctly. Removing quote marks and replacing single quote marks with double quotes hasn’t made a difference. I can’t find anything online that’s worked, can anyone on here see where I’m going wrong?

Is use Openmqttgw for sending rf433 commands via mqtt. I can’t test the templates now but I don’t recall the payload being send in json.
Also the shouldn’t be the topic be

home/OpenMQTTGateway/433toMQTT

Instead of

/home/OpenMQTTGateway/433toMQTT

I think this will do the trick:

- alias: 'OMG Light Toggler'
  trigger:
  - platform: mqtt
    topic: 'home/OpenMQTTGateway/433toMQTT'
  action:
  - service: light.toggle
    data_template:
      entity_id: >-
        {% set rooms = { '11073208':'master_bedroom', '12540548':'lounge_tv', '3735524':'hallway_light'} %}
        light.{{ rooms[value] if value in rooms.keys() else 'master_bedroom' }}

Ah I see what you did there. Unfortunately with that template every switch I have toggles the master bedroom light on the else case. Unless I’m reading it wrong at what point is it searching the JSON string to find the value? There’s a reference to value but none to trigger.payload_json.

@subzero79 from my experience wtih MQTT I don’t think the leading / makes much of a difference as long as they’re all looking for the same topic.

Oops! My mistake. I was a little too quick with the old copy 'n paste! You’re right, it needs to reference what triggered the automation.

Untested but should work: :wink:

- alias: 'OMG Light Toggler'
  trigger:
  - platform: mqtt
    topic: 'home/OpenMQTTGateway/433toMQTT'
  action:
  - service: light.toggle
    data_template:
      entity_id: >-
        {% set rooms = { '11073208':'master_bedroom', '12540548':'lounge_tv', '3735524':'hallway_light'} %}
        light.{{ rooms[trigger.payload_json.value] if trigger.payload_json.value in rooms.keys() else 'master_bedroom' }}

As for this part:

else 'master_bedroom' 

That’s to ensure some sort of default entity_id is supplied. If the payload contains a value that isn’t in the rooms list, you still have to supply something to satisfy the service’s requirements. If you supply nothing then light.toggle will attempt to run without a valid entity_id and Home Assistant will report it as an error.

The leading / in the topic won’t break anything but it’s unnecessary. From MQTT’s perspective it sees it like this: nothing/home/OpenMQTTGateway/433toMQTT. Effectively, you’re wasting one level in the hierarchy.

Ah OK makes sense.

Your fixed template didn’t work unfortunately but I’ve managed to figure out why and fix it. All I did was remove the single quote marks from the defined integers. So instead of your template I had this:
{% set rooms = { 11073208:'master_bedroom', 12540548:'lounge_tv', 3735524:'hallway_light'} %}
As opposed to this:
{% set rooms = { '11073208':'master_bedroom', '12540548':'lounge_tv', '3735524':'hallway_light'} %}

Looking at the JSON string received on MQTT, there are no quote marks in any of the actual values either, so it looks like Hass was trying to compare an integer against a string. This might be part of the reason my original series of ifs didn’t work either but using a case select is far more elegant anyway.

I thought that was the case when I had a closer look at my original condition: statement and noticed they weren’t there either.

Anyway thank you once again for your help!

Correct! In the payload, value is an integer, not a string.

I’d like to claim that I purposely leave a few simple bugs in my examples so that they make it more of a collaborative learning experience. Unfortunately, I cannot, in good conscience, make that claim. :slight_smile:

1 Like

To be honest I should have spotted it the first time round! I had them on throughout my first post. Your template is still infinitely better than mine so I’m glad I started the thread if only for that!