#[Solved] How do I filter a blueprint's inputs by state?

1 messages ยท Page 1 of 1 (latest)

scenic sierra
#

Hello hello, I have a blueprint with a light entity selector input and want to turn them off based off of a trigger. I noticed that sometimes my lights shift color after a while, and I think this happens due to them being sent a turn on event with no data while they are already on. I want to filter the lights that are already on out of this action. How do I do this?

frank galleon
#

Assign the input to a variable, then you can do a select('is_state', 'off')

scenic sierra
#

So at the root of the yaml, add:

variables: 
  _lights_on: !input lights_on

And in the target of the action

{{  _lights_on | select("is_state", "off") | list }}

If I try this, I get an empty list and the action errors out, despite the lights definitely being off.

  1. Why does this result in an empty list?
  2. How do I prevent an empty list from causing an error in a light.turn_on action?
scenic sierra
#

Maybe relevant: the only thing actually in the input is an area

frank galleon
#

Ah OK, in that case you need to get the light entities in that area
area_entities(_lights_on) | select('search', 'light') | select('is_state', 'off') | list

Then before your light on command do an if with a template to check the length of the list is >0

scenic sierra
#

Will that also work if I have normal entities in _lights_on? Preferably I would have both types allowed

frank galleon
#

i don't understand what you mean tbh

scenic sierra
#

Currently there is one area in the input, but in the GUI I can also select individual entities. I would like the blueprint to work in both cases. If I use area_entities, would it still work for those individual entities?

#

This is the selector for the blueprint input

frank galleon
#

ah i see. are you also going to be pulling in labels and devices?

scenic sierra
#

I'd like the option to, yeah.

frank galleon
#

ok, then it's a little more complicated but not too bad

#

Something like:
{{ (_lights_on + _lights_on | map('area_entities') | list + _lights_on | map('label_entities') | list + _lights_on | map('device_entities') | list) | select('search', 'light.') | select('is_state', 'off') | list }}

scenic sierra
#

Yeah ok, filter out the various possible types and combine them, that makes sense. I'll try it out soon, thanks!

frank galleon
#

it actually is a bit dumber than that cos there's no way to determine if it's a label or whatever in the template

scenic sierra
#

Should probably store this in a variable too so I can easily check the length and trigger turning them on without copying the whole thing twice

frank galleon
#

so it just says "treat all of these as a label and see what i get" - for things that aren't labels (i.e. areas/devices/entities) it just returns nothing

scenic sierra
#

Yeah that makes sense

#

I kind of expected HA to handle this itself, to be honest

frank galleon
#

i mean.. i've never run into this issue you're having anyway

scenic sierra
#

Is it that rare to have an input that accepts areas, devices, entities and labels?

frank galleon
#

this is how it works normally:

action: light.turn_on
data: {}
target:
  label_id: house_lights
  entity_id: light.main_bedroom_lights
#

you have to define them separately because they need to be treated differently

#

but given that you want to do an entity-level filter on them, you need to pull out the entitites you care about

scenic sierra
#

I see, I see

#

Yeah I don't understand why the IKEA tradfri lights seem to suddenly reset to full brightness, max coldness and this is just one attempt to fix it ๐Ÿ˜…

scenic sierra
frank galleon
#

oh, that's easier then

#

{{ (_lights_on['entity_id'] + _lights_on['area_id'] | map('area_entities') | list + _lights_on['label_id'] | map('label_entities') | list + _lights_on['device_id'] | map('device_entities') | list) | select('search', 'light.') | select('is_state', 'off') | list }}

scenic sierra
#

That makes sense. Does that work even if there is only one area? That makes the value for area_id not a list but a key

frank galleon
#

i dunno man, i've never tried to do this before

#

should do though

scenic sierra
#

Hahaha ok I'll try it out, thanks!

#

Nope, that complains about the dict not having those keys...

#

{"area_id": ["hallway","office"]} doesn't have entity_id so it fails

whole egret
#
{% set my_keys = _lights_on.keys() %}
{% set ents = [] if 'entity_id' not in my_keys else _lights_on['entity_id'] %}
{% set a_ents = [] if 'area_id' not in my_keys else _lights_on['area_id'] | map('area_entities') | list  %}
{% set l_ents = [] if 'label_id' not in my_keys else _lights_on['label_id'] | map('label_entities') | list %}
{% set d_ents = [] if 'device_id' not in my_keys else _lights_on['device_id'] | map('device_entities') | list %}
{{ [ents,a_ents,d_ents,l_ents]|flatten|select('match', 'light.') | select('is_state', 'off')  | unique | list }}

EDIT: It's a bit more readable if you set variables

scenic sierra
#

Getting more and more complicated hahaha

#

Can this be stored in a variable?

whole egret
#

Yes

scenic sierra
#

Harder to debug though I feel, it just says unknown error if something is wrong ๐Ÿค”

#

[Error in describing condition: Cannot read properties of undefined (reading 'includes')]
Executed: April 23, 2026 at 11:06:59 PM
Result:
result: false
entities: []

#

On the condition that's just a template it fails

#
{% set my_keys = _lights_on.keys() %}
{% set _lights_on = {'area_id': 'hallway'} %}
{{ ([] if 'entity_id' not in my_keys else (_lights_on['entity_id'] | list) 
+ ([] if 'area_id' not in my_keys else _lights_on['area_id'] | map('area_entities') | list) 
+ ([] if 'label_id' not in my_keys else _lights_on['label_id'] | map('label_entities') | list )
+ ([] if 'device_id' not in my_keys else _lights_on['device_id'] | map('device_entities') | list)) 
|flatten | select('match', 'light.') | select('is_state', 'off')  | unique | list}} 

Trying this in the template editor complains about _lights_on not existing, I'm confused

#

Oop nvm I see

#

It seems to return a list of empty lists instead of a list of entities

#

Oh it's because it's looping over every letter in the word 'hallway'...

#

[_lights_on['area_id']] | flatten should work

#

Both when it's a list and a string

scenic sierra
#
{% set _lights_on = {'area_id': ['hallway', 'wc'], 'entity_id': 'light.office_ceiling'} %}
{% set my_keys = _lights_on.keys() %} 
{{ 
(([] if 'entity_id' not in my_keys else [_lights_on['entity_id']] | flatten )
+ ([] if 'area_id' not in my_keys else [_lights_on['area_id']] | flatten | map('area_entities') | flatten )
+ ([] if 'device_id' not in my_keys else [_lights_on['device_id']] | flatten | map('device_entities') | flatten )
+ ([] if 'label_id' not in my_keys else [_lights_on['label_id']] | flatten | map('label_entities') | flatten ))
| unique | select('match', 'light.') | select('is_state', 'off') | list }} 
#

This works!

#

Well, it looked like it would work

#

Error: dictionary update sequence element #0 has length 21; 2 is required

On the target of the turn on action...

#

Got it!!!

#

Took forever to figure out but I understand templating a lot better now. Thank you both!