I am trying to find the best way to trigger an action based on last_changed?
Check every 30 minutes from last_changed, if the garage door is open, send notification.
Trying to avoid:
trigger:
- minutes: /30
platform: time_pattern
It triggers based on the current time, every half hour, and hour. If it is 5 minutes till the hour, it will trigger in 5minutes, not 30 minutes.
Currently, I have the following setup and working, but is there a better way?
Configurations.yaml
######################################################
# Time from last change in minutes
# Divide minutes by 30
# For loop (24 hours = 48 half hours)
# If minutes divided by 30 equals a whole number
# Set state of the sensor to 'open'
######################################################
sensor:
- platform: template
sensors:
garage_timer:
value_template: >
{% set duration = ((states.sensor.time.last_changed - states.cover.garage_door.last_changed).total_seconds() / 60) | round(0) %}
{%- set time_check = (duration / 30 ) -%}
{%- for i in range(0, 48) -%}
{%- set check = (time_check == i) -%}
{%- if check == true %}open{% endif -%}
{%- endfor %}
- platform: time_date
display_options:
- 'time'
Automations.ymal
- id: 'TEST_OPEN_30'
alias: Garage Door Open (30min)
description: ''
trigger:
- entity_id: sensor.garage_timer
platform: state
to: open
condition:
- condition: and
conditions:
- condition: state
entity_id: cover.garage_door
state: open
action:
- data:
data:
actions:
- action: close_garage_door_now
title: Close Garage Door?
- action: ignore
title: Ignore?
vibrationPattern: 100, 1000, 100, 1000, 100
message: Garage Door is OPEN!
title: Home Automation
service: notify.mobile_app_My_Phone
mode: single
This looks like a good candidate for the lastest automation changes outlined in https://www.home-assistant.io/blog/2020/07/22/release-113/ which all can be done from a single automation without the need of an additional template sensor.
Thanks for sharing. This looks like a great solution to an issue I also want to solve. It seems the only difference between your and my setup is that you are using a cover entity and I have a door sensor which is listed as a binary sensor. I tried to modify the code like this:
configurations.yaml
sensor:
- platform: template
sensors:
entrance_timer:
value_template: >
{% set duration = ((states.sensor.time.last_changed - states.binary_sensor.haustuer.last_changed).total_seconds() / 60) | round(0) %}
{%- set time_check = (duration / 30 ) -%}
{%- for i in range(0, 48) -%}
{%- set check = (time_check == i) -%}
{%- if check == true %}open{% endif -%}
{%- endfor %}
- platform: time_date
display_options:
- 'time'
automations.yaml
- id: '1599636801727'
alias: Alarm when Entrance door open for 30 min
description: ''
trigger:
- entity_id: sensor.entrance_timer
platform: state
to: open
condition:
- condition: and
conditions:
- condition: state
entity_id: binary_sensor.haustuer
state: open
action:
- data:
data:
actions:
- action: close_entrance_door_now
title: Close Entrance Door?
message: Entrance Door is OPEN!
title: Home Automation
service: notify.mobile_app_thomasiphone
mode: single
I can’t see any error in the logs but the issue is that the action (phone message) never will be fired. Any help would be appreciated. I also couldn’t find out how to get the value for states.binary_sensor.haustuer.last_changed to debug it a bit more.
Ok, I checked out “Alert” and the Config Variable: notifiers requires notification integration. However, I do not see the Moblie Companion App option and therefore can’t send the actionable notification that allows me to close the garage door from my phone.
Am I missing something?
alert:
garage_door:
name: Garage is open
done_message: Garage is closed
entity_id: input_boolean.garage_door
state: 'on'
repeat:
- 30
can_acknowledge: true
skip_first: true
notifiers:
- **??????????????**
I think the Automation Mode: Restart “Start a new run after first stopping previous run.”
I added a 30 min delay and the
- id: 'TEST_OPEN_30'
#########################
# See the first post
#########################
- delay: 00:30:00
mode: restart
I tried the Automation Modes Restart and Queued. However, they didn’t seem to work as I excepted. Restarted seemed to trigger even when the door was closed and queued I couldn’t get to trigger again. I also tried using a wait_template, assuming it would exit the queued loop if the door was closed.
For notifiers that require other parameters (such as twilio_sms which requires you specify a target parameter when sending the notification), you can use the group notification to wrap them for an alert. Simply create a group notification type with a single notification member (such as twilio_sms) specifying the required parameters other than message provided by the alert component:
Hey Thomas, I am fairly new to Hassio and am learning as I go.
I had to make a small change to the for loop **{%- for i in range(0, 48) -%}*, starting the loop at 0 was setting the check to be true. Change it to {%- for i in range(1, 48) -%}.
For debugging, I use the Developer Tools > TEMPLATES.
{{states.sensor.time.last_changed}} you should see the output of the right “2020-09-11 21:10:00.074934+00:00”
Something for states.binary_sensor.haustuer.last_changed
{{states.binary_sensor.haustuer.last_changed}}
You can use {{states.binary_sensor.haustuer}} and you should see your state options.
Great. Thanks so much also for the debugging help with it. Sadly it still doesn’t work for me. Would be be ok with you pasting your complete code for this automation (related parts of automation and configuration.yaml) here please. I sense there must be another slight difference. Thank you very much.
Good idea, I adjusted the whole thing for myself and also optimized a little. Here without template, directly as a template trigger in the automation and a group for all checked entities:
- alias: Door - Door open longer 5 minutes
id: auto_door_5min_open
mode: parallel
max: 10
max_exceeded: warning
trigger:
- platform: template
value_template: >-
{% set output = namespace(state=false) %}
{% for entity in (expand('group.grp_door') | rejectattr('state','in',['unknown','unavailable']) | map(attribute='entity_id')) %}
{% if (states(entity) == 'on') %}
{% set duration = ((now() - states[entity].last_changed).total_seconds() / 60) | round(0) %}
{% if duration > 0 and duration % 5 == 0 %} # 5 Minuten
{% set output.state=true %}
{% endif %}
{% endif %}
{% endfor %}
{{- output.state -}}
variables:
meldung_entity_id: >-
{% set members = namespace(entities=[]) %}
{% for entity in (expand('group.grp_door') | rejectattr('state','in',['unknown','unavailable']) | map(attribute='entity_id')) %}
{% if (states(entity) == 'on') %}
{% set duration = ((now() - states[entity].last_changed).total_seconds() / 60) | round(0) %}
{% if duration >= 5 %} # 5 Minuten
{% set members.entities = members.entities + [entity] %}
{% endif %}
{% endif %}
{% endfor %}
{{- members.entities -}}
action:
- repeat:
for_each: " {{- meldung_entity_id -}} "
sequence:
- service: script.script_sonos_say2 # script to say something or ...
data:
mp_entity_id:
- group.grp_sonosmedia_tts
message: >-
{% set duration = ((now() - states[repeat.item].last_changed).total_seconds() / 60) | round(0) %}
{{- state_attr(repeat.item,'friendly_name') + ' bereits ĂĽber ' + (duration|string) + ' Minuten offen' -}}
- delay:
seconds: 5