How to use timer that resets based on motion, and finally kicks off an automation?

Hi,

I would like to set up a timer that starts counting (1440 minutes) from the last detected motion (‘on’).
If there is a new motion within the 24 hours (1440 minutes) window, reset the timer and start over.
If the timer then hit 1440 minutes, I want to run an automation.

This is how far I’ve come:
Configuration.yaml:

timer:
  motion:
    duration: '24:00:00'

Automations.yaml (start timer on motion):

- alias: Timer
  id: 'Timer'
  trigger:
  - platform: state
    entity_id: sensor.motion
    to: 'on'
  action:
  - service: timer.start
    entity_id: timer.motion

Configurations.yaml (when timer times out):

- alias: Timerstop
  id: 'Timerstop'
  trigger:
  - platform: event
    event_type: timer.finished
    event_data:
      entity_id: timer.motion
  action:
  - service: notify.notify
    data:
      message: "Timer is finished"

Could anybody please help me with this one where the timer resets if there is a new motion detected while the timer is running?

To do it without the timer you could just trigger like this:

- alias: Timer
  id: 'Timer'
  trigger:
    - platform: state
      entity_id: sensor.motion
      to: 'off'
      for:
        hours: 24
  action:
    - service: notify.notify
      data:
        message: "Timer is finished"
2 Likes

Hi @tom_l Great idea - had to read the code two times, had written a different answer first :slight_smile: I will test this now…

1 Like

Just an FYI, the state trigger’s “for” parameter uses the entity’s last_updated field, which effectively gets reset when HA restarts. That means after a HA restart, the automation won’t trigger for at least 24 hours, even if the motion sensor has been off for 24 hours sometime before that. This isn’t much of an issue if HA doesn’t restart often. But when it does restart, just be aware it will cause this automation to take at least 24 hours before it can trigger.

One way to get around that is to use the History Statistics Sensor. This sensor uses data stored in the database, which spans restarts. You can define a sensor whose value will be the amount of time sensor.motion has been ‘on’ in the last 24 hours. Then you can trigger your automation when the value of that sensor becomes zero. (You might even define a template binary_sensor that is ‘on’ whenever the history sensor is non-zero, and then trigger the automation when the binary_sensor changes to ‘off’.)

Just an idea. And although this solution is less vulnerable to HA restarts, it’s not entirely unaffected by them either. Obviously while HA is not running (which is at least a small amount of time while HA restarts, but can be longer if HA is stopped and later started again) it can’t know what the motion sensor is doing. But at least it’s slightly better than a simple state trigger w/ the “for” parameter.

BTW, I only mention this because the period of the “for” parameter is relatively large. If it were a few seconds or minutes, it might be “good enough.” :slight_smile: Then again, it’s probably good enough if your system doesn’t often restart, or if the side effect I described is not an issue for you.

2 Likes

Good point and excellent solution.

1 Like

cool now I can say “if you kill me this want change anything, if i don’t go back within the next few hours the data will be sent automatically”

but as i’m not in a film… i’m wondering what I could do with this. Anyway the solution is nice straighforward

I could use this to disable the alarm for ex… but i’m not sure that I can override the end trigger time of an arlo alarm :

@pnbruckner ohhh, this is far above my knowledge - would you be so kind to show an example? :slight_smile:

sensor:
  - platform: history_stats
    name: Last 24hr Motion
    entity_id: sensor.motion
    state: 'on'
    type: time
    duration:
      days: 1
    end: "{{ now() }}"
binary_sensor:
  - platform: template
    sensors:
      motion_in_last_24hrs:
        friendly_name: Motion in Last 24hrs
        value_template: "{{ states('sensor.last_24hr_motion')|float > 0 }}"
automation:
  - alias: Do something when no motion for 24 hours
    trigger:
      platform: state
      entity_id: binary_sensor.motion_in_last_24hrs
      to: 'off'
    action:
      ...
1 Like

@pnbruckner Thank you so much!

I want to use the slider to be able to change the interval in realtime, so I’ve created:

input_number:
  motion_timer:
    name: Motion Timer
    icon: mdi:timer
    initial: 30
    min: 0
    max: 1440
    step: 1 

Can I insert {{ states(‘input_number.motion_timer’)| int }} like this?:

  - platform: history_stats
    name: Siste 24 timer Motion
    entity_id: binary_sensor.hue_motion_sensor_1_motion
    state: 'on'
    type: time
    duration:
      minutes: "{{ states('input_number.motion_timer')| int }}"
    end: "{{ now() }}"

Duration does not accept templates. You’d have to calculate the start.

EDIT:

  - platform: history_stats
    name: Siste 24 timer Motion
    entity_id: binary_sensor.hue_motion_sensor_1_motion
    state: 'on'
    type: time
    start: >
      {% set ts = as_timestamp(now()) - states('input_number.motion_timer')| int * 60 %}
      {% set fmat = "%Y-%m-%d %H:%M:%S" %}
      {% set tstring = ts | timestamp_custom(fmat) %}
      {{ strptime(tstring, fmat) }}
    end: "{{ now() }}"
1 Like

@petro, sorry mate, didn’t activate the sensor ‘sensor.siste_24_timer_motion’ at all, though there was no error messages either

@pnbruckner I have your solution working but have a strange problem;
The motion sensor itself (‘sensor.motion’) kick off immediately, but, the sensor created under ‘history-stats’ takes approx 30-32 seconds to pick up the motion (and of course, the binary sensor kick off at the same time as the ‘history_stats’ sensor).

What can cause this delay?

@petro, could I insert a template in this automation (picked up from input_numer ‘motion_timer’)?
Meaning, replace the minutes part with a template like (this one I didn’t get to work);

    for: 00:{{states ('input_number.motion_test') | int }}:00 
- alias: 08 - Timer Test Motion
  id: Timer Test Motion
  initial_state: 'off'
  trigger:
  - entity_id: sensor.hue_motion_sensor_1_motion
    for: 00:02:00
    platform: state
    to: 'on'
  action:
  - data:
      message: 08 - Timer Test Motion is finished
    service: notify.stigh

EDIT: Changed the automation, now slider works by changing ‘for’ in the trigger to using ‘delay’ in the action like this:

- id: 09 - Timer Test Motion using Slider
  alias: 09 - Timer Test Motion using Slider
  trigger:
  - entity_id: sensor.motion_stue
    platform: state
    to: Klar
  action:
  - delay: '00:00:{{ states.input_number.motion_timer.state | int }}'
  - data:
      message: 09 - Timer Test Motion w/Slider is finished
    service: notify.stigh

Of cource, the delay get screwed up if it is at ex 24 hrs and I do a reboot within that delay. This is where the ‘history_stats’ from @pnbruckner comes in. Though, as stated in another post; I’m hit by the fact that is the motion sensor is passed a few seconds after last scan_interval and changes state back to ‘off’ before next scan_interval, the ‘history_stats’ is not triggered.

Like most sensors, they update periodically, with the default being every 30 seconds. This would be when it queries the database to see what recent changes have happened with the entity it’s monitoring. You can change the update rate using the standard scan_interval configuration variable.

Ah, okie - but increasing scan interval will impact the entire HA and hardware resources as the load will be a lot heavier on the system (I guess).

The thing is that if the flag is not raised to ‘on’ from the motion sesnor at the moment the scan interval occur, it will not be picked up. This means you can actually pass the sensor 3 seconds after last scan interval and the motion sensor changes from ‘on’ to ‘off’ before next interval = no triggering.

Can I set a scan_interval inside

sensor:
  - platform: history_stats
    scan_interval: 5
    entity_id: binary_sensor.hue_motion_sensor_1_motion

which will only affect the interval of checking for change of the motion sensor?

Yes, that’s how you would change the polling interval for that one particular sensor. It will cause it to query the database every 5 seconds instead of every 30 seconds, and of course will add some load to the system. But, depending on the hardware you’re using, and what else your system is doing, it may not even be noticeable.

No, that’s not how this works. Whenever the motion sensor changes state (to ‘on’, or to ‘off’), that will be recorded in the database. The history_stats sensor periodically queries the database to see how long the sensor was (cumulatively) ‘on’ during the last 24 hours (or whatever period you specify.) If it goes ‘on’ at all, the history_stats sensor will see it, no matter when it polls/queries, even if it was only on for a few milliseconds.

That can’t be true, as I’m fully able to trigger the motion sensor (I see it go from ‘off’ to
on’ and back to ‘off’) without triggering the ‘history_stats’ and according binary_sensor that should be triggered by the history_stats’ sensor (hope you understand what I’ trying to tell :slight_smile: )

Can you post your current definition of the history_stats and binary_sensors?

Please notice I’ve changed the timer in the sensor to 2 minutes for testing purposes.

sensor:

  - platform: history_stats
    scan_interval: 5
    name: Siste 24 timer Motion
    entity_id: binary_sensor.hue_motion_sensor_1_motion
    state: 'on'
    type: time
    duration:
      minutes: 2
    end: "{{ now() }}"

binary_sensor:

      motion_siste_24t:
        friendly_name: Motion siste 24t
        value_template: "{{ states('sensor.siste_24_timer_motion')|float > 0 }}"

automation:

- alias: 99 - Do something when no motion for 24 hours
  id: Do something when no motion for 24 hours
  trigger:
  - entity_id: binary_sensor.motion_siste_24t
    platform: state
    to: 'off'
  action:
  - data:
      message: Timer history_stats are finished
    service: notify.stigh

Ok, thanks.

What does the history of binary_sensor.hue_motion_sensor_1_motion, sensor.siste_24_timer_motion & binary_sensor.motion_siste_24t look like when motion is detected?