Issue when using own attributes in template sensor

Hello!
I want to define the used physical temperature sensor(s) of a template sensor just once in the attributes section to prevent errors when changing the physical sensors. So I created following:

template:
  -
    sensor:
      -
        name: radiators_bath_min_temp
        unit_of_measurement: °C  
        device_class: temperature
        state_class: measurement
        attributes: # This defines the involved sensors.
          physical_temp1: sensor.th03_temperature
          physical_temp2: sensor.th05_temperature
        availability: >-
          {{ 
          not is_state(this.attributes.physical_temp1, 'unavailable') and
          not is_state(this.attributes.physical_temp2, 'unavailable') 
          }}
        state: >-
          {{ [states(this.attributes.physical_temp1)|float,
              states(this.attributes.physical_temp2)|float] | min }}

In principle this works fine, but I get an error message in the logs at each HA startup, that physical_temp1 and physical_temp2 are undefined.
I read, that the states section is performed before the attributes section, which would explain this behaviour. But I have also read, that availability section is performed before state section, which would not explain this (in my understanding exactly this case is the reason for the availability section?!).
I also tried to use a default value in the state

state: >-
          {{ [states(this.attributes.physical_temp1)|float(0),
              states(this.attributes.physical_temp2)|float(0)] | min }}

but this has disadvantages:

  • There is still an error message in the logs
  • There are several seconds with a wrong value which could trigger automations.

What I would like to have:

  • Until physical_temp1 and physical_temp2 are undefined, the state of radiators_bath_min_temp should be undefined, too.
  • There should be no error message in the logs at startup.

Any ideas?

The use of a default value of 0 in float(0) can’t compensate for an undefined variable. Therefore your template needs to test if this.attributes.physical_temp1 is defined before it attempts to use it. In fact, it may first need to confirm that this.attributes is defined.

Thanks!
I agree, that a default value of float(0) is not the solution.
But isn’t the availability section exactly the check if this.attributes is defined?
Or is there any other way to do this check?

Sure, except your availability template isn’t performing that check. It’s immediately using it in a states() function without first confirming it’s defined.

Okay, I think I see the problem. But how to check if the attribute is defined without/before a states() function?

See if this helps (untested).

        availability: >-
          {% set temp1 = this.attributes.physical_temp1
            if this.attributes is defined and
              this.attributes.physical_temp1 is defined 
            else '' %}
          {% set temp2 = this.attributes.physical_temp2
            if this.attributes is defined and
             this.attributes.physical_temp2 is defined 
            else '' %}
          {{ temp1 != '' and temp2 != '' and
            not is_state(temp1, 'unavailable') and
            not is_state(temp2, 'unavailable') }}

Thank you, very interesting to see what is possible with templates!

Unfortunately this doesn’t work. If I implement this code, I see in the States tab in the Developer Tools, that the entity doesn’t have my attributes. If I understood correctly, the reason is, that the attributes section is executed after the state section. But the state section is not executed, as the availability section returns false. And this false comes, as the attributes section is not evaluated. So there is a classical deadlock.

My idea is now, to implement a similar template in the state section: If the attributes are defined, the wanted value is returned. If the attributes are not defined, I would like to return the unavailable state. This should prevent the deadlock.

But how to set a state to unavailable? I assume that {{ unavailable }} returns a string.

Did it eliminate the error message that you said occurs at startup?

Yes, it eliminates all error message, as the critical part is not executed any more. But the price for this is, that the sensor does not work any more, because the state section is never executed as the availability section returns always false.

That’s the reason why I would like to implement a similar code in the state section, but have no idea how to return “unavailable” as state.

So it fulfills the second of the two stated requirements:

  • Until physical_temp1 and physical_temp2 are undefined, the state of radiators_bath_min_temp should be undefined, too.
  • There should be no error message in the logs at startup.

The first requirement is that the sensor’s state should be “undefined”. There are two non-nominal state values: unknown and unavailable. What I have suggested employs unavailable. Did you want it to report unknown (or something else)? Or are you saying it fails to report unavailable for the sensor’s state value?

Correct. That’s how it’s designed to work. If the availabilitytemplate evaluates to false, the sensor’s state value is set to unavailable.

Maybe I was not precise enough: My two stated requirements are of course additional to the implicit requirement, that the existing and intended function (to calculate the min() of the two soensors) is still available :wink:
Without this, the template sensor is useless.

Indeed, the “undefined” in my requirement should be “unavailable”.

You are correct, that your proposed code gives an “unavailable” for the state. But this “unavailable” never vanishes. My wish is that the state in “unavailable” until the attributes are defined and available. If this is given, the state should be the min() of the two temperatures.

I think you will have to accept the fact that Template Sensors weren’t designed to support what you are attempting to implement (effectively, to define an always-available variable in an attribute). Owing to the way state and attributes (and availability) are processed, at some point it may lose the variable you have defined.

FWIW, a Trigger-based Template Sensor can define variables in its action section. However it can’t be used the way you want (eliminate duplication of entity_ids; at a minimum, they must be defined in the trigger).

You may wish to consider voting for the following Feature Request:

Thank you very much for your work!
As this is more an optical problem (to have no errors in the logs at startup) it is no real problem to live with the situation. I will also check the feature request.

Maybe a last thing to complete my picture: I understood, that a false in the availability will result in an “unavailable” for the state. But is there any way, to set the state to “unavailable” from inside the state section itself? I didn’t read a clear “no” until now.

Remove the availability option and use a modified version of its template, combined with a modified version of the existing state template, to report the minimum temperature or unavailable when appropriate.