How to convert an string to a int in a template?

I have an slider that duplicates a fan speed slider but just for a subset of the supported speeds.

The fan has 11 speeds, I use just from 1 to 6.

The problem I have, is that when calling the fan.set_percentage my request fails because the value is send as an string instead of an int:
image

How can I make the template render an int or a float?

This is the full code:

type: slider
entity_id: fan.esp_ventilation_controller_fan_1
range:
  - 9.09
  - 54.55
tap_action:
  action: perform-action
  target:
    entity_id:
      - fan.esp_ventilation_controller_fan_1
  confirmation: false
  perform_action: fan.set_percentage
  data:
    percentage: > 
      {{ value | float }} 
step: 9.090909090909092
value_attribute: percentage

Thank you.

Using the “regular” Fan controller sends the same data on the websocket but of course as a number.

Error says an int is expected, you are filtering to a float. Just change float to int?

If that doesn’t do it, edit your tags so it ends up in the correct forum. This does not seem like a frontend question but something that has to do with ESPHome…?

Changing it to an int works, but does not send 45.4545 but "45" which technically is the wrong value.

I will open an issue on HA core since sending 45.4545 as number works, but I think the endpoint should also map it from an "45.4545" string.

It could lead to errors I think.

So how much difference is 45% vs 45.4545% in the actual fan speed?
I bet this bug report will be closed faster than you can type it.

It does say int so 45.4545 is an invalid input. Most likely it just truncate it in the background.

2 Likes

We’ll… Because that call only accepts integers… filtering in int() intentionally drops the decimal because that’s what integers are. Whole number only.

This statement says my destination only supports whole numbers because when I send floating point it blows up.

What Hellis is says here is absolutely correct. The remainder is insignificant. It’s a fraction of a percentage and probably exactly why it’s dropped. Floating point math is expensive computationally and you don’t use it when you don’t need to.

I mean concur, but the thing is, HA forces us to use percentages in fans and then we have to use workarounds to convert them. It would be so easily be used with speed 1 to 6.

And like I show on my screenshot above, the official fan entity also sends that pretty 45.454545454545454 value. :man_shrugging:

Doesn’t matter what the fan sends. That call takes an integer… It won’t ever take anything else. What the sensor actually displays is not associated with the input to the call.

I am talking of the UI Call while using this:

There is no special code there, just the vanilla fan controller from HA. If I change that slider and see the webworker event, THAT component sends their value as percentage xx.yyyyyyyyyyy values (as number).

Edit:

What I meant is that it is inconsistent design. I can live with it, but I still see it as a long hanging fruit fix.

Oh i feel ya but remember that number is a sensor coming out of the fan. It is controlled by that fan controller.

But… (this is the important part) It has absolutely no bearing on what the fan.set_percentage call accepts THAT is controlled by HA. Because it’s the twisted into whatever format your device actually needs and HA has to deal with thousands of devices. They’ve come to the conclusion for fan set percent an integer is good enough and simplifies things…

Whether your (or my Jasco, or someone’s Inovelli) fan controller stores it to 87000 digits of precision or not honestly, its not nor should it be the fan.set_percentage call’s problem. It abstracts all of that and allows int. That’s what it needs. Whole number from 0-100. Period.

Its easy to work around… We know it only takes an int so just surround the input with x | int(0) and done… (and is best practice because you should ASSUME all other things being passed in HA are strings unless you specifically handled it)

You can’t assume because you see it in the UI as x it needs to be sent as x.

Kind of similar to another issue I filed earlier today. Lights in HASS have a brightness range of 0–255 integer, but because Zigbee ascribe some special significance to a brightness value o f0xFF, the developers of ZHA have in their infinite wisdom decided that reported brightness should cap out at 254. This leads to other weirdnesses such as if you ask light.turn_on to use brightness_step_pct: -50 from starting brightness 100% i.e. 254, you end up with a new absolute value of 126. Which to the great annoyance of anyone with OCD will display as 49% on the dashboard.

In my opinion, precisely because HASS has to support thousands of different devices, but generally itself runs on more powerful hardware (even a Raspberry Pi today is powerful compared to anything from 10 years ago), there is no reason whatsoever to not always use sensible ranges for internal representations. Why the heck would you use a brightness of 0–255 integer when you could use 0–100% float?!

Exact same for light color temperature. The only non-deprecated property is color_temp_kelvin, but internally the value is still stored as a mired integer. This makes it so that the value displayed on the dashboard will never ever be the exact same as the one you feed into light.turn_on due to limited precision in forwards and backwards conversions.

0 to 255 is the range most hardware uses under the hood. It’s pretty much an industry standard for anything that adjusts light levels.