List variable in a loop behave like a local to the loop

I want to create a list that contains the name and the battery level of all the entities that have batteries and the battery level is below 90.
For this, I made a loop that accumulates the entities that match the condition to a list. I checked it in the “template editor” in the developer tools and it works as expected.
However, in the automation, the list variable returns an empty value. Even so, the list variable (ns.devices) is defined as “namespace”.
It seems the list variable (ns.devices) behaves like a local variable in the automation. below is the code from the automation.

  • Core: 2025.5.0
  • Supervisor: 2025.04.1
  • Frontend: 20250507.0
variables:
  low_battery_devices: |
    {% set list = [['aa','bb']] %}
    {% for s in states
        if s.attributes.device_class == 'battery'
        and s.state is not none
        and s.state not in ['unknown', 'unavailable']
        and s.state | regex_match('^\d+(\.\d+)?$')
        and (s.state | float) < 90 %}
      {% set name = s.attributes.friendly_name if 'friendly_name' in s.attributes else s.entity_id %}
      {% set percent = s.state | float(0) | round(0) | int %}
      {% set list = list + [name ~ ' (' ~ percent ~ '%)'] %}
    {% endfor %}
    {{ list }}

Please follow Questions Guideline #11 by formatting your configuration example properly.

You can make you template more efficient by limiting it to the sensor domain instead of checking the state object of every entity in your system by using states.sensor in the second line instead of just states.

If your question is about an automation, you should post the automation’s configuration (properly formatted), not just a variable definition.

And in this case it is important to know what version you are running. Scoping of variables in automations changed in version 2025.4

1 Like

This guy has a great video that does what you want…
HOW TO create your own Low Battery Warning Sensor In Home Assistant - TUTORIAL

1 Like