Elegant automation for 3 temperature input and 2 fans

cool.
I’d advise you to take a look at the docs to make sure your config is following the requirements (just noticed that you quote values of above/below)

Looks like you’re using Automation editor… you can make your automations shorter and learn faster/more if you do it manually (but it’s absolutely fine if you like it) :wink:

Yes, I am using Automation editor to start with and then I am editing the file sometime checking with editor how it looks and if it is OK.
Also template editor in Developer tools is very helpful.
Qute values are coming from the editor. Is it wrong ?

My dream and target is to create ONE automation for this purpose. :slight_smile:

it seems like you don’t need to quote values for above and below but if it works, don’t bother.

could you explain why is it your dream?

UPDATE: actually, looking at your automations I can see some reasons. Well, if the separate automations work as expected, we’ll look into it.
Could you tell me why #3 and #4 use different ways to change state of the switch, is it intentional?

I believe it will be easier to troubleshoot in case something is wrong. Also if one piece of “code” is controlling behaviour of one solution it is easier to change and adjust (as opposite I can make some change in one automation, like some treshold, and then not notice that the other one there is older treshold or it does not correspond to changes made in first one.

No, not intentional. When using Automation editor initially i have used “call service” for action and then I realised I can use “Device” as action type. Is there any suggestion which one would be better ?

ok, let’s have a lot at your description and the automations.
this

and this

is a bit controversial, could you clarify? no fans should be running if CEL <= 12C?

Yes. 12C is the target temperature I would like to have in my cellar.
So, as long as it is below 12C (it may happen in the strong winter as the room does not have any heating) I do not need to cool it down - so do nothing.
The second quote you have made refers to the same target and I wanted to explain that while any of the fan is working and temperature drops below 12C then any fan (OUT and GWC( should be off as the target has been reached.

So here’s how I see it now:
Let’s talk temperature sensors and switches for clarity.

Is it correct to say that to decide what to do we need to observe the following rules:
0. if CEL <= 12, turn off both switch.out and switch.gwc

else:

  1. turn_OUT_on = (OUT+2) < CEL < (OUT-2)
  2. turn_GWC_on = (GWC+2) < CEL < (GWC-2)
  3. if turn_OUT_on is True, turn on switch.out and turn off switch.gwc
    else if turn_GWC_on is True, turn on switch.gwc and turn off switch.out
    else turn off both switch.out and switch.gwc

Does it sound correct?

Thanks.
rule 0 confirmed.
The rest I would write slightly different:

    1. turn_OUT_on = (OUT+2) < CEL
    2. turn_GWC_on = (GWC+2) < CEL 
    3. if turn_OUT_on is True,
          turn on switch.out and turn off switch.gwc
       else if turn_GWC_on is True
          turn on switch.gwc and turn off switch.out
      else
          turn off both switch.out and switch.gwc

Does this make sense ?

you just removed CEL < (OUT-2) and CEL < (GWC-2).
I don’t mind, but it was by your initial request, isn’t it?

Sorry, it seems I was not clear enough. My assumption

was related to the same condition. If OUT temperature is lower then CEL by 2 degrees turn the OUT fan ON. In case it is not lower (in my words: OUT temperature rises above this 2 degree limit) then turn the OUT fan off.
The same goes for GWC temperature and fan.
The idea is that fan should not pomp the air inside the cellar if the temperature outside (or in ground system) is higher then CEL temp - 2 degrees, as in that case cellar is not chilled any more.

Ok, now we’re clear with the algo and can discuss a code.
Are you ready to produce it now or need some help/hints?

From what I see it won’t be the most elegant automation at least because Jinja’s variables are limited by boundaries of a template and you’ll need at least 2 (to control both switches).
And you’ll probably need 2 automations - one for rule 0 and another for the rest (but I’m not sure without the actual code).

I think I would like to get some help/hints.
I have used/copied this one for controlling light:

alias: AUTO - lights
  trigger:
  - entity_id: binary_sensor.pir1_gospodarczy
    platform: state
    to: 'on'
  - entity_id: binary_sensor.pir1_gospodarczy
    for: 0:00:12
    platform: state
    to: 'off'
  action:
 entity_id: switch.swiatlo_gospodarczy
   service_template: |-
  {% if trigger.to_state.state == "on" %}
    homeassistant.turn_on
  {% elif trigger.to_state.state == "off" %}
    homeassistant.turn_off
  {% endif %} 

and I like it as it is one for turning the lights on and off and also have this nice feature that the light is ON for defined time after sensor has stopped detecting movement.

that’s all good and stuff but you have 2 switches, remember? :wink:
so it won’t be as elegant as this one.
have you tried modifying it yet?

Yeah… it is more challenging.
No, I have not tried to modify this.

Ok, try this and let me know how it goes.

- alias: elegant_automation
  trigger:
    platform: template
    value_template: >
      {% set normal_temp = 12 %}
      {% set delta = 2 %}
      {% set invalid_states = ['unknown', 'unavailable'] %}
      {% set cmd_out = 'off' %}
      {% set cmd_gwc = 'off' %}

      {% set temp_cel = states('sensor.cel') %}
      {% if temp_cel not in invalid_states and temp_cel|float > normal_temp %}
        {% set temp_out = states('sensor.out') %}
        {% set temp_gwc = states('sensor.gwc') %}

        {% if temp_out not in invalid_states and (temp_out|float + delta) < temp_cel|float %}
          {% set cmd_out = 'on' %}
        {% elif temp_gwc not in invalid_states and (temp_gwc|float + delta) < temp_cel|float %}
          {% set cmd_gwc = 'on' %}
        {% endif %}
      {% endif %}

      {{ states('switch.out') != cmd_out or states('switch.gwc') != cmd_gwc }}

  action:
    - service_template: >-
        switch.turn_
        {%- set normal_temp = 12 -%}
        {%- set delta = 2 -%}
        {%- set invalid_states = ['unknown', 'unavailable'] -%}
        {%- set cmd_out = 'off' -%}

        {%- set temp_cel = states('sensor.cel') -%}
        {%- if temp_cel not in invalid_states and temp_cel|float > normal_temp -%}
          {%- set temp_out = states('sensor.out') -%}

          {%- if temp_out not in invalid_states and (temp_out|float + delta) < temp_cel|float -%}
            {%- set cmd_out = 'on' -%}
          {%- endif -%}
        {%- endif -%}
        {{ cmd_out }}

      data:
        entity_id: switch.out

    - service_template: >-
        switch.turn_
        {%- set normal_temp = 12 -%}
        {%- set delta = 2 -%}
        {%- set invalid_states = ['unknown', 'unavailable'] -%}
        {%- set cmd_gwc = 'off' -%}

        {%- set temp_cel = states('sensor.cel') -%}
        {%- if temp_cel not in invalid_states and temp_cel|float > normal_temp -%}
          {%- set temp_out = states('sensor.out') -%}
          {%- set temp_gwc = states('sensor.gwc') -%}

          {%- if temp_out not in invalid_states and (temp_out|float + delta) < temp_cel|float -%}
          {%- elif temp_gwc not in invalid_states and (temp_gwc|float + delta) < temp_cel|float -%}
            {%- set cmd_gwc = 'on' -%}
          {%- endif -%}
        {%- endif -%}
        {{ cmd_gwc }}

      data:
        entity_id: switch.gwc

As I said, it’s not always the best idea to put everything in one automation, especially using Jinja.

2 Likes

OK. Great ! Had a time now to put it into automations file. Will see now, how it works.
Thank your for your help - it is for me also great learning as I love to do it on practical, live examples. Let ask few questions as the learning concerns:

  1. I “{%” string indicating that now we are entering a programming area (in python ?) ?
  2. What is the difference between {% , {%- and {{ ? I have tried to find it in google with little success. Maybe you can point me to good reference ?
  3. Can this be written the way that {% is at the beginning of first line and then at the end of last line, instead of the beginning and end of each line ?
  1. nope, it’s Jinja template
  2. no need to go so deep now. it just converts newlines/whitespaces into one whitespace or so (-). {% and {{ - read the link above
  3. no, each statement need its own one.

as I said, it won’t be elegant.
for more elegant stuff you can try python_script, but it’s not a proper python as well so… :\

Its working great ! Thank you again.
I may need to change “delta” or adjust some conditions.
Another “learning” questions:
4. What is the purpose of if temp_xxx not in invalid_states ? The temperatures reading will be always fine so there is no risk that reading will be “unknown or unavailable” ?
What is the risk to remove this condition ?
5. Is seems this automation works “always”. I mean that even if I change the fan switch manually it immediately returns to the position forced by automation. I was thinking that Automation only “works” once the trigger fires it up and trigger will “trigger” only when some of the sensor change their state/value ?

when you make your automation work as tired we can tweak it so it uses dynamic data that user can change from frontend, for example (if needed).

If for whatever reason your sensor becomes unavailable (unknown usually means the entity does not exist) and you have no such if, you might get unexpected behaviour (paste this {{ 'unknown' | float }} in template editor). Using my approach it just does nothing and cmd_xxx remains off so no errors, no false on actions. Yo can add issuing a custom warning/error to logs.

that’s because the automation reacts on state change of sensor.cel, sensor.out, sensor.gwc, switch.out and switch.gwc.

see above. there’s no such thing as value, it’s change of state (which includes change of any attributes so the actual state string may remain unchanged and still the trigger will fire).

1 Like

@AhmadK
Thank you again for support here! The automation is working perfectly and I am a happy “automation master” in my home ;). I also did dynamic user data (entry from frontend) of level and delta and adjust the trigger section.
I learned a lot here. Thanks !

If you are so kind and check my another challenge here: 8 relay board - RS232-USB controll - integration Any direction/pointer will be more then appreciated !