Turn off a light if left on solidly for an hour?

I’m trying to setup a light switch so that if the light is left on for an hour it turns off.

The intent is that if the light is switched on, and left on uninterrupted for an hour, to turn off the light. If any state changes happen in the meantime, then abort.

My initial attempt looks like this:

alias: "Failsafe: Turn off Main Ensuite Lights if on for over an hour"
description: ""
trigger:
  - platform: state
    entity_id:
      - light.sw_mainbedroom_ensuite_lights_switch
    from: "off"
    to: "on"
    for:
      hours: 1
      minutes: 0
      seconds: 0
condition:
  - condition: device
    type: is_on
    device_id: 0d1fd20e597288eb04eb2833dc4b0fe8
    entity_id: 92531d87e30ff8ceaca72dac0018f97f
    domain: light
action:
  - type: turn_off
    device_id: 0d1fd20e597288eb04eb2833dc4b0fe8
    entity_id: 92531d87e30ff8ceaca72dac0018f97f
    domain: light
mode: single

This doesn’t work. What happens is that when the light switches from “off” to “on”, Home Assistant starts waiting for an hour. If the light is turned on and off in the meantime, then the state trigger remains active but is never inspected until the 1 hour is up - at which point, if the light is on, it gets turned off - even if it was toggled on and off multiple times in the interim.

This honestly isn’t what I expected out of the “for” directive, since this feels like it should read as “if the light went from off to on for 1 hour” not “if the light goes from off to on and then 1 hour later the state is still on”.

This problem seems to be a variant of the “extend active time if motion re-detected” issue, and this automation was based off a comment here that the state entity will give me this behavior, but it doesn’t seem to.

What am I missing?

There’s the Mode option, Restart, for automations that may apply - not that I’ve taken advantage of 'em myself, yet.

  1. For trigger: Use platform device, turned_on for the trigger with the “for” as you have.
  2. No condition needed
  3. action looks good.

Use the editor, as it will make sure everything is formatted correctly

alias: "Failsafe: Turn off Main Ensuite Lights if on for over an hour"
description: ""
trigger:
  - platform: device
    type: turned_on
    device_id: 0d1fd20e597288eb04eb2833dc4b0fe8
    entity_id: 92531d87e30ff8ceaca72dac0018f97f
    domain: light
    for:
      hours: 1
      minutes: 0
      seconds: 0
condition: []
action:
  - type: turn_off
    device_id: 0d1fd20e597288eb04eb2833dc4b0fe8
    entity_id: 92531d87e30ff8ceaca72dac0018f97f
    domain: light
mode: single

Don’t do this. See Why and how to avoid device_ids in automations and scripts

I have automations like this and they work. Home Assistant does start timing again after the second change.

Yes that is exactly what it does. The light needs to be on continuously for one hour for the trigger to occur. That includes not changing to unavailable.

If your automation is not doing that, look at the automation trace and light history to determine what happened.

Reloading the automation or restarting home assistant will cancel this trigger.

Okay, the winner is @bob.t who had the right of it: the issue here is that the mode has to be set to restart otherwise the trigger is never reset after initial activation.

Near as I can tell, there’s nothing special about the “for” trigger - it doesn’t seem to cancel if the trigger becomes “untrue”, or at least having a “from” to “to” transition prevents it from being cancelled.

It’s possible the problem is that I’m looking for “off to on” and not just “is on”.

2 Likes

That trigger transition logic (changes from FROM to TO) seems sound, Will. To me, anyway. [shrug]

I’ve just utilized restart on a frequently triggered automation to monitor how well I understand how to use that option myself. :upside_down_face:

An interesting but incorrect conclusion. The value of mode isn’t even a factor for your automation.

mode determines what the automation should do when it’s triggered while it’s still busy executing its actions. For your automation, which spends virtually no time at all executing its action, the value of mode is irrelevant.

A State Trigger’s for option works exactly the way tom_l explained.

  • A state-change from off to on serves to start an internal 1-hour timer.
  • Any state-change during the timer’s countdown will reset the timer’s countdown.
  • If there’s no state-change during the entire 1-hour countdown, then at the end of the countdown the State Trigger is triggered.

It has worked like this for many years.


FWIW, a long duration for runs the risk of being cancelled by a restart. In other words, if you restart Home Assistant at any time during the 1-hour countdown, the for’s countdown is cancelled and not resumed when Home Assistant starts.

1 Like

So I just tried this now with a 20 second delay and in single execution mode, and you’re right, it seemed to work correctly:

alias: "Failsafe: Turn off Main Ensuite Lights if on for over an hour"
description: ""
trigger:
  - platform: state
    entity_id:
      - light.sw_mainbedroom_ensuite_lights_switch
    from: "off"
    to: "on"
    for:
      hours: 0
      minutes: 0
      seconds: 20
condition:
  - condition: device
    type: is_on
    device_id: 0d1fd20e597288eb04eb2833dc4b0fe8
    entity_id: 92531d87e30ff8ceaca72dac0018f97f
    domain: light
action:
  - type: turn_off
    device_id: 0d1fd20e597288eb04eb2833dc4b0fe8
    entity_id: 92531d87e30ff8ceaca72dac0018f97f
    domain: light
mode: single

This might be an issue of human falliability: since the goal is to switch the lights off it they’re left on, the problem is quite possibly that if they’re on I’ve walked in without flicking the switch (it’s in an awkward place to reach, hence the automation).

So I suspect the correct answer is I really do need a motion sensor.

EDIT: Marking this as the solution - problem I suspect was between desk and chair.

Thanks for laying it out. I understand. In my case, automations worked as intended, but I thought the warnings that were generated were unnecessary, and thought the RESET option would stop them. I don’t think the warnings were of any concern otherwise, but as I poke around and review what I’ve set up so far (curious to understand HA under the GUI better). . . you know. :slight_smile:

Not sure if/when using RESET in an automation is the right choice, but it’s early for me in this endeavor.

Then do this:

mode: single
max_exceeded: silent
1 Like

As was suggested by @tom_l you need to check that the state of the light does not change to unavailable or any other state during that one hour window.

For long running timers like this - I prefer to use a timer.

trigger:
  - platform: event
    event_type: timer.finished
    event_data:
      entity_id: timer.mylight
    id: timer_done
  - platform: state
    entity_id: light.mylight
    to: on
    from: off
    id: light_on
action:
  - choose:
      - conditions:
          - condition: trigger
            id: light_on
        sequence:
          - service: timer.start
            target:
              entity_id: timer.mylight
            data:
              duration: "01:00:00"
      - conditions:
          - condition: trigger
            id: timer_done
        sequence:
          - service: light.turn_off
            target:
              entity_id: light.mylight

If the light changes to unavailable in this time, it will not reset the timer when it changes back to on. Editing automations will also not reset the timer, and I believe - though I am not totally sure - that restarting Home Assistant will not affect the timer either.

A pointer in the right direction.

Thank you, Tom. . . and Will.