If statement in automation to determine triggers "for:" time

Hi,

I’m trying to use my Hue motion sensor and Hue light in bathroom to change how long the light is on after there is no motion. The normal time would be 5 minutes when all is normal. The second situiation is when the humidity is over 50. Humidity is measured by different sensor. This is the code I have tried:

- alias: "Bathroom lights off when no motion"
  trigger:
    platform: state
    entity_id: sensor.bathroom_motion_sensor
    to: 'off'
    for:
      minutes: {{ 15 if sensor.zha_01ddaf89_1_1029.state >= 50 else 5 }}
  condition:
    condition: time
    after: '07:00'
    before: '00:00'
  action:
    service: homeassistant.turn_off
    entity_id: light.bathroom

The humidity sensors state is the humidity in int. The code works if I just put in minutes the value 5.

You can’t use a template in the trigger as you are. It’s going to be complicated to get it just right but try the following in your trigger section:

trigger:
  - platform: template
    value_template: "{{ (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state < 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_changed)) / 60 )| int > 5) or (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state >= 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_changed)) / 60 )| int > 15) }}

So basically the template above says “if the humidity is below 50% and the motion sensor is off for longer than 5 minutes” then trigger. OR “if the humidity is greater than 50% and the motion sensor is off for longer than 15 minutes” then trigger.

I think. I don’t have you exact entities so I can’t test the substitutions I made to the template but I’m pretty sure I got it right.

Thanks for the reply!

The code does not give any errors but also does not trigger the lights off. So I have Hue motion sensor that is turning the lights on but nothing happens when the off automation should trigger.

The value that Hue motion sensor is for the last movement is in format:
“last_updated: 2019-01-06T09:23:55”

If you go to the dev tools state page and click the box to the left of the automation, in the box that pops up click on the “trigger” and see if the lights turn off.

Also it might help to post your entire off automation code again as you have it in your config right now just to make sure everything still looks ok there.

It does trigger! So that part of the code works. I changed the minutes to make testing easier.

Here is the code

- alias: "Bathroom lights off when no motion"
  trigger:
  - platform: template
    value_template: "{{ (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state < 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 1) or (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state >= 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 2) }}"
  condition:
    condition: time
    after: '07:00'
    before: '00:00'
  action:
    service: homeassistant.turn_off
    entity_id: light.bathroom

you’d probably best create an extra template binary sensor and use that as trigger.

have a similar setup with a template_binary sensor based on a regular motion_sensor:

  master_bedroom_motion_sensor_timed:
    friendly_name: 'Master bedroom motion sensor timed'
    value_template: >
      {{ is_state('sensor.master_bedroom_motion_sensor','on')}}
    delay_off:
      minutes: 1
    device_class: motion

and use that as trigger for the automation.

OK the next thing to do is copy only the actual template portion from the value_template and paste it into the dev-tool template editor and see what the result is on the right side. It should return either “True” or “False”.

And just as a dummy check :slightly_smiling_face: it is between 0700 & 0000 where you are located correct?

It does not return anything, just blank. The time is correct, i double checked that :slight_smile:

well, that’s strange…

I don’t have any of the entities that you have and when I copy your template and paste it into my template editor with no changes at all I still get “False” returned.

OK I guess we need to split things up to see where it is failing for you.

first copy this and paste it into your template editor and see what the result is:

{{ (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state < 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 1) }}

then if that returns true or false then copy & paste this into the editor:

{{ (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state >= 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 2) }}

tell me the results of those.

It does not return anything. I tried to split it into even smaller and it seems that

{{ (states.sensor.zha_01ddaf89_1_1029.state > 50) }}

is returning nothing but I change “>” to “==” it returns false.

Could the reason be on that? That sensor is Xiaomi temperature sensor that is connected with ZHA module and hardware is Elelabs zigbee raspberry shield.

Edit: I try again, it needs ‘’ around it.

try wrapping the 50 with single quotation marks ( ‘50’ ) and leave the “>” in place.

EDIT: nevermind that. I figured out the issue. I hope…

I forgot that the state of the humidity detector is a string so you will need to convert it to an int to make it work.

try this:

{{ (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state | int < 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 1) or (states.sensor.bathroom_motion_sensor.state == 'off' and states.sensor.zha_01ddaf89_1_1029.state | int >= 50 and ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 2) }}

OK, now it return “true” as a whole. But still does not seems to trigger in automation.

I just edited my post above…

Still the same, it now returns false and does not trigger :confused:

That sounds like progress to me!

now you need to start checking the individual things in the trigger.

You said before that you broke them up into smaller sections. Did they all return false?

try these:

{{ states.sensor.bathroom_motion_sensor.state == 'off' }}

{{ states.sensor.zha_01ddaf89_1_1029.state | int < 50}}

{{ ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 ) | int > 1 }}

{{ states.sensor.zha_01ddaf89_1_1029.state | int >= 50 }} 

{{ ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 2 }}
{{ states.sensor.bathroom_motion_sensor.state == 'off' }}

This returns “true” because the state is “off” currently.

{{ states.sensor.zha_01ddaf89_1_1029.state | int < 50}}

This returns true.

{{ ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 ) | int > 1 }}

This returns false.

{{ states.sensor.zha_01ddaf89_1_1029.state | int >= 50 }} 

This returns false

{{ ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 2 }}

This returns false

how long has it been since the motion sensor went to “off”?

What is the value of:

{{ ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 ) | int }}

Now that value is “1”. Currently it is over 10minutes when that changed to off.

{{ ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 ) | int > 1 }}

Now this returns true

and

{{ ((as_timestamp(now()) - as_timestamp(states.sensor.bathroom_motion_sensor.last_updated)) / 60 )| int > 2 }}

This returns false

Edit: Both are true now and that what you put previous is now 0.

And now what is the value of the entire template? it should be true, correct?