Dinamically modifying automation activation time

Hi, I’m a beginner with HA, and would like to know if it’s possible to change on-the-fly the activation time of an automation, which e.g. should be executed at 07:00 during winter and at 08:00 during summer. Of course there are a lot of automations to affect, and several time bands to set, thus I need an elegant way to avoid replicating a lot of automation differing only for the activation time…

Is it possible?

Thank you guys!

The basic answer is to use a time-only Input Datetime Helper in your Time trigger.

Luckily, there are other options. If the Helper + Time trigger option doesn’t work for what you are trying to do, please clearly explain why not and what functionality you need so we can give you options that are more specific to your situation. Depending on your exact needs, there are a number of other time-related ways to trigger automations, each with their own strengths and weaknesses.

Here are a couple general options to consider:

Calendar triggers

Sun Triggers

Schedule entities (used with State trigger)

Templates


FWIW, many users start out with time-based automations, but they usually end up causing significant frustration, especially if you live with other people. Most of us just don’t live out our lives following a strict enough schedule.

Please describe the desired outcome. What’s the end goal?

1 Like

Hi, many thanks for the answer… I have set about 30 automations (10 for workday, 10 for pre-festive and 10 for festive days); the activation time of these automations should be different depending on the season. Thus I should set up a total of about 120 automations (30 * 4), differing only for the activation time: I created the first 30 automations for Winter where, along with the time/weekday I check that the current date is inside the range defined by the helpers Winter_Begin and Winter_End.

In order to avoid the repetition of 90 more automations where the only differences are in the activation time for the different seasons, as a programmer my idea was to set only 30 automations and make a script or a piece of YAML which, at the beginning of a new season, modifies the activation time of each atomation: e.g.

Automation_1 at 7:00 in Winter → 8:00 in Spring, 9:00 in Summer, 6:45 in Autumn

Automation_2 at 9:45 in Winter → 10:45 in Spring, 11:15 in Summer, 9:30 in Autumn

Hope I explained my needs clearly enough :slight_smile:

Thank you

Have a look at this: Seasonal automation management

This I would consolidate into a Template sensor (or Template select), so that you have one source of the current “season” which can be referenced everywhere. I would do the same with the “day type”.

To do something along the lines you described, you could have a single Input Datetime Helper for each automation. If you are going to be doing this, you might as well consolidate the season and day type into each helper reducing 30 total automation to 11 (the extra one sets the values of the ten helpers every day).

So each automation would have a trigger something along the lines of:

triggers:
  - trigger: time
    at: input_datetime.automation_trigger_1

Then you would have an automation that triggers at the start of each day to set the appropriate values to the helpers. There are a number of ways to do this. One option would be to set up a variable mapping the object IDs of the helpers to their possible time values, then use a Repeat for Each to iterate through them all.

Automation Sketch: Setting Helper values using 'look up table' and Repeat
triggers:
  - trigger: time
    at: "01:00:00"
variables:
  season: "{{ states('sensor.current_season') }}"
  day_type: "{{ states('sensor.day_type') }}"
  helpers:
    automation_trigger_1: 
      Winter:
        workday: "07:00:00"
        pre_festive:
        festive: 
      Spring:
        workday: "08:00:00"
        pre_festive:
        festive: 
      Summer:
        workday: "09:00:00"
        pre_festive:
        festive: 
      Autumn:   
        workday: "06:45:00"
        pre_festive:
        festive: 
    automation_trigger_2: 
      Winter:
        workday: "09:45:00"
        pre_festive:
        festive: 
      Spring:
        workday: "10:45:00"
        pre_festive:
        festive: 
      Summer:
        workday: "11:15:00"
        pre_festive:
        festive: 
      Autumn:   
        workday: "09:30:00"
        pre_festive:
        festive: 
conditions: []
actions:
  - repeat:
      for_each: "{{ helpers.keys() | list }}"
      sequence:
        - action: input_datetime.set_datetime
          data:
            time: "{{ helpers[repeat.item][season][day_type] }}"
          target:
            entity_id: "input_datetime.{{ repeat.item }}"

The benefits of this approach are that you reduce 30 (or 120) automations to 11.


If you want to stick with the 30 automations, another option would be to structure the automations so they each have all four season triggers:

Automation Sketch using season time triggers
triggers:
  - trigger: time
    at: "07:00:00"
    id: Winter
  - trigger: time
    at: "08:00:00"
    id: Spring
  - trigger: time
    at: "09:00:00"
    id: Summer
  - trigger: time
    at: "06:45:00"
    id: Autumn
conditions:
  - condition: template
    value_template: "{{ trigger.id = states('sensor.current_season') }}"
actions:
....

This might actually be a bit easier to manage since the trigger times are local to where they are being used.

If it is just 30 minutes or an hour, you could also just add a delay ?

description: ""
mode: single
triggers:
  - trigger: time
    at: "07:00:00"
conditions: []
actions:
  - choose:
      - conditions:
          - condition: template
            value_template: |-
               {% set m = now().month %}
               {{ m == 12 or m == 1 or m == 2 }}
        sequence:
          - delay:
              hours: 1
              minutes: 0
              seconds: 0
              milliseconds: 0
        alias: Winter?
      - conditions:
          - condition: template
            value_template: |-
              {% set m = now().month %}
              {{ m == 3 or m == 4 or m == 5 or m == 9 or m == 10 or m == 11 }}
        sequence:
          - delay:
              hours: 0
              minutes: 30
              seconds: 0
              milliseconds: 0
        alias: Spring / Autumn?
  - action: light.turn_on
    metadata: {}
    data: {}

This would add an one hour delay in winter months, and a 30 minutes delay in spring/autumn (and no delay in summer).

There is a but though; it would not survive if you reboot within the time window.

What do the automations do differently depending on whether it’s a workday, pre-festive, or festive?

Because I sense the potential to reduce the count to 10 automations (employing Didgeridrew’s suggestion) that perform different actions depending on season and time period.

Sorry… the 30-minutes delays were only an example… the activation times can be any…

Thank you anyway!
Sergiopa

Success!
I wrote a template sensor which returns the string of the season:
template:

  • sensor:
    • name: “Season”
      state: >
      {% set Date = {
      “Month”: now().month,
      “Day”: now().day
      } %}
      {# Winter: Dic (after 20), Gen, Feb, Mar (before 21) #}
      {%- if (((Date.Month == 12) and (Date.Day >= 21)) or (Date.Month == 1) or (Date.Month == 2) or ((Date.Month == 3) and (Date.Day < 21))) -%}
      Winter
      {# Spring: Mar (after 20), Apr, Mag, Giu (before 21) #}
      {%- elif (((Date.Month == 3) and (Date.Day >= 21)) or (Date.Month == 4) or (Date.Month == 5) or ((Date.Month == 6) and (Date.Day < 21))) -%}
      Spring
      {# Summer: Giu (after 20), Lug, Ago, Set (before 21) #}
      {%- elif (((Date.Month == 6) and (Date.Day >= 21)) or (Date.Month == 7) or (Date.Month == 8) or ((Date.Month == 9) and (Date.Day < 21))) -%}
      Summer
      {# Autumn: Set (after 20), Ott, Nov, Dic (before 21) #}
      {%- else -%}
      Autumn
      {%- endif -%}

then I put the following condition in the automations:
{{ (states (‘sensor.Season’) == trigger.id) }}

Everithing worked fine! Many thanks guys!

FWIW, you can compact your template quite a bit by using tuple comparison:

sensor:
    name: "Season"
    state: >
      {% set Date = (now().month,now().day) %}
      {# Winter: Dic (after 20), Gen, Feb, Mar (before 21) #}
      {% if (12,21) <= Date or Date < (3,21 %}
        Winter
      {# Spring: Mar (after 20), Apr, Mag, Giu (before 21) #}
      {% elif (3, 21) <= Date < (6,21) %}
        Spring
      {# Summer: Giu (after 20), Lug, Ago, Set (before 21) #}
      {% elif (6, 21) <= Date < (9,21) %}
        Summer
      {# Autumn: Set (after 20), Ott, Nov, Dic (before 21) #}
      {%- else -%}
        Autumn
      {%- endif -%}

And, if you want to make it a bit more efficient for your system, you could add a couple triggers so that it only updates a few times a day rather than every minute.

1 Like

It worked… many thanks! :grinning:

Why do you want/need different times by season?

If you’re using season as a proxy for varying sunrise/sunset times or weather (e.g. sky brightness, temperature), then triggering off these directly tends to be more elegant. E.g. HA lets you trigger X minutes before sunrise or when the outdoor lux level goes above or below a certain level.

Hard-coding times by season can easily feel clunky unless you live your life uniformly in 4 distinct 90-day blocks. Real life tends to be messier; e.g. the sky can go dark in the middle of the day due to a storm, you might get up extra early or late one day, there could be a heatwave in the winter or cold snaps in fall, etc. A home that reacts gracefully to these tends to be more enjoyable.

Tuning 120 hard-coded times (4 season times x 30 automations) if/when you find some of them aren’t quite right also gets tedious fast.

Hi, you are right… but this HA installation is for a church, thus there are a lot of lights to turn on and off at different times, and the times also depend on the “season” (that furthermore could not coincide with astronomical or metereological seasons, thus I need a customizable formula to calculate “seasons”).

In addition, in HA there are switches to force a workday as festive or pre-festive, overriding the standard schedules… Another switch “Funeral” should override everithing for few hours, and at the end, the standard schedules should return active.

Sergio

Got it. That’s helpful context.

For the festive/funeral overrides, have you considered using HA’s Google Calendar integration to set/control your override switches? This makes it easy for your non-technical users to add/view/edit events remotely without touching HA.

It supports multiple calendars, so you could as example create one for festive periods and another for events like funerals and weddings. E.g. we use one calendar to turn on a helper switch when the kids are off school (to override school morning routines) and another for when we’re expecting visitors (to nudge up the heating and lighting).

Your template uses:

  • December 21
  • March 21
  • June 21
  • September 21

By how much do those dates differ from the ones used for astronomical seasons?


Answer: About +/- 1 day, depending on the year.

What religious convention (for lighting) requires each season to start exactly on the 21st?