Best Practices for Setting Up Automations and Scripts in Home Assistant

Hello everyone,

I would like to ask for your advice regarding the setup of automations and scripts within Home Assistant.

Currently, I have several automations running in Node-RED. I chose this option at the time because I found it to be clear and the management seemed easier. However, with the recent developments in automations in Home Assistant, I am considering gradually transitioning to this functionality and phasing out Node-RED.

Before I take this step, I have a few questions:

  • How many automations do you typically use?
  • How and when do you implement a script, especially with management in mind?
  • Does the number of automations or scripts significantly impact the performance of Home Assistant?

To make my question a bit more concrete, I want to share an example: My children each have their own button next to their bed to turn on their nightlight and the central bedroom lamp. Additionally, they can also turn on the hallway light. How would you translate something like this into an automation or script?

  • Should I set each button as a separate automation?
  • Can I migrate to one automation with multiple conditions
  • Or is it better to combine automations with scripts?

I have included a screenshot of Node-RED below for clarification.

I look forward to hearing your experiences and advice!

Best regards,

You could use trigger variables.
So each event is a separate trigger in the automation, and accompanied there are variables with the % and entity name.
The action could probably be just a light turn on with the variables being the entity and percentage.

I would not use scripts for this. This is far to simple, adding scripts will just make it more complex and harder to follow

1 Like

100%

Always the first question -
First, Do I NEED an automation or script. (In most cases probably not or there’s another construct that already does the thing. Let’s assume I do.)

If I do, I then ask myself, what’s the simplest way to do it using HA built-in constructs. (For instance, if I’m trying to glue together a synthetic media console I use a Universal Media Player - not just a bunch of scripts because the endgame presents a media player so the rest of the system (and my LLM) can use it.

Then when I need to build automations / scripts, remember automations are just scripts with a trigger. Scripts can accept variables while automations on the other hand (yes, I’m ignoring the entire trigger variables discussion for now). Therefore, in my setup Automations are mostly just triggers ‘we need to do a thing now’. I then build a script accepting vars to ‘do the thing’ when necessary and then use automations to trigger those scripts.

For instance, scripts:

accept variables (fields)

Get called by automations:

Which marshal the when and why…


^^^ All those codepaths are just different cases for when triggers fire.

Yes, this is the most EXTREME version but that’s how I use it.

  • Script by default
  • Automation if I need a trigger
  • Automation calls script to do stuff if it’s more complex than an ‘If this then that’ call
  • don’t build a script if you don’t have to

I’m currently on over 200 automations and over 160 scripts and so far, so good. I haven’t gone COMPLETELY crazy - yet. (just mostly)

As many as needed to get the job done. That said most often I only need 1 automation.

I try to avoid using any script because they tend to make debugging the action next year more complicated. What was I thinking when I made that script. An automation is like a script and will cover 99% of everything you might need.

Not really. HA can handle hunderds of automations without any sweat.

I 100% disagree with this one sorry ashai.but I understand why you’d say it. For my setup it actually makes things easier. I see a trigger. Fired script A with these vars. Here’s the trace from A. Otherwise there is not really a difference troubleshooting IMHO now INTENT_SCRIPTS on the other hand… :sunglasses:

Choice is good.

Hehehe, not offended. But to be honest. Your setup is not a normal setup. It is more like a hypersonic spaceship with a still to invent hyperdrive in the back. In your case i surely would also use scripts. As a software developer that will give me far more control. But i still believe that for everyday use automations will do nicely.
The thing is that when a solution works it just works for a long time. No need to look at it anymore till is isn’t. Having a lot of scripts makes debugging less easy if you haven’t looked at them for a year or so.
That is so in my case. I create a solution and when it is working it can forget about it and work at other things.

1 Like

The thing with scripts is that most use them as substitutes for the exact same thing.
As in this case (as far as we can see from the image) we need entity and percentage and a light turn on.
So we are going to replace the light turn on in the automation with a script call which then has a light turn on.
So what did we gain on that?

Same thing with a notification, people set up scripts where you feed it with message and title. :man_shrugging:

I reserve scripts to something I would use multiple times and the script should contain at least 3 steps otherwise I don’t see the point.
You just made debugging harder as Ashai says in my opinion.
Sure I would know the issue is in either the automation or the script, or scripts.
But still, that leaves me with at least two places to look for a cause, in most cases that is not my preferred way.

2 Likes

Same. I’m not using them for trivial crap. I agree with you in what most use them for and why I harp on ‘do I need it’

But having the ability to break stuff up when it gets REALLY complicated is helpful and I can’t imagine trying to manage it any other way. It’ll also fit in automation construction as they start using the new targeting paradigm.

Unless you have very inefficient automations (meaning the automations run more than they need to), you probably won’t notice performance issues, directly related to the number of automations you have.

The time you might notice is when a major event happens (for example first person to arrive home), since HA has to do a bunch of stuff at once **.

In my case I notice a slight “wave” of actions as the actions fire in sequence - TBF its still under a second and if you are not explicitly looking for it you wouldn’t notice - kinda like a flickering light doesn’t bother you until you notice it.

** - I don’t think this is actually a HA issue, I think its “backing up” sending all the commands over Zigbee.

I generally find that most automations follow common patterns:

  • Motion detected → turn on light.
  • Button pressed → toggle something on/off

I typically use 1 automation per pattern, regardless of the number of devices that it controls, so for example I have a single automation that handles all of my presence/motion detectors.

I find that having a lot of branching in automations or scripts is what makes them difficult to read, therefore I used “tricks” to try to eliminate most (and occasionally all) branching.

For example here is my motion detected automation:

mode: single
alias: Motion Detected
description: ""
triggers:
  - trigger: state
    entity_id:
      - input_select.sensor_mode
      - binary_sensor.sensor_group_bedroom
      - binary_sensor.sensor_group_hall_delayed
      - binary_sensor.sensor_group_living
      - binary_sensor.sensor_group_closet
      - binary_sensor.sensor_group_kitchen_combo
conditions: []
variables:
  present_bedroom: "{{ is_state('binary_sensor.sensor_group_bedroom',       'on') }}"
  present_hall: "{{    is_state('binary_sensor.sensor_group_hall_delayed',  'on') }}"
  present_living: "{{  is_state('binary_sensor.sensor_group_living',        'on') }}"
  present_closet: "{{  is_state('binary_sensor.sensor_group_closet',        'on') }}"
  present_kitchen: "{{ is_state('binary_sensor.sensor_group_kitchen_combo', 'on') }}"
  active_mode: "{{ states('input_select.sensor_mode') }}"
  scene_map:
    "Off": []
    Day:
      - selector: input_select.hall_lighting
        value: Bright
        present: "{{ present_hall }}"
      - selector: input_select.kitchen_lighting
        value: "{{ states('input_text.kitchen_lighting_last') }}"
        present: "{{ present_kitchen }}"
      - selector: input_select.bedroom_lighting
        value: Day
        present: "{{ present_bedroom }}"
      - selector: input_select.closet_lighting
        value: Bright
        present: "{{ present_closet }}"
    Night:
      - selector: input_select.hall_lighting
        value: Red
        present: "{{ present_hall }}"
    Away:
      - selector: input_select.living_lighting
        value: Arm
        present: "{{ present_living }}"
  active_setting: "{{ scene_map[active_mode] }}"
actions:
  - repeat:
      for_each: "{{ active_setting }}"
      sequence:
        - action: input_select.select_option
          metadata: {}
          data:
            option: "{{ iif(repeat.item.present, repeat.item.value, 'Off') }}"
          target:
            entity_id: "{{ repeat.item.selector }}"

Tricks:

  • All presence sensors are in groups (some groups only have one sensor).
  • This is an “input” automation, so I take inputs and update “helper” input selects - it may do a little more than it needs to, but at the end of the day its only updating UI (helper) elements.
  • I use a map (scene_map) instead of doing a condition in the actions section, hence my house modes (Off, Day, Night & Away) are all defined in the scene_map.
  • The scenes to activate are defined as lists, therefore I can have any number of them without needing an if condition. Additionally if I don’t want any actions I simply use an empty list (as in the case of the Off sensor mode).
  • There is also an Off scene for every room, so I don’t need a special case I just activate the Off scene.

Note: There is an accompanying “output” automation that reads the helpers and applies scenes (to change the lights). The output automation only fires if the select actually changes, so it doesn’t matter if input automations fire a little more than needed, as nothing actually happens.

I don’t always split “input” and “output” automations, but I often find there are multiple input automations and only a single output, so it saves duplicating the output logic multiple times (my scene switches update the same UI helper selects, hence re-use the same output automation as the motion detectors).

In answer to your question (about script usage) I have refactored my scripts/automations so that I don’t have to have any scripts, however I have 3 scripts which are invoked by my “Button Pressed” automation, so that I can have 3 clear sections/functions (Scenes, AC, House Modes).