djtimca / haomnilogic

Hayward Omnilogic integration for Home Assistant available through HACS
Apache License 2.0
18 stars 6 forks source link

Setting Pump Speed Errors out in HA, though Changes Speed #13

Closed N3rdP1um23 closed 2 years ago

N3rdP1um23 commented 2 years ago

Hey! I was playing around with the pump side of things and was able to follow #9 to add a slider, have it update when the pump updates (through the Omnilogic app or manually using the Pool controller), and have added some automation as well!

However, I've now simulated your "set speed buttons" and when it calls the service, I receive the following error "Cannot set speed on a non-variable speed pump" even though a few seconds later I can see that the gauge has changed successfully.

Before image

After image

As mentioned earlier, the gauge updates (as it's using the value directly from the filter speed sensor and not the number entity) and I've also confirmed in the OmniLogic app that the speed has in fact changed.

Here's the error that I can see in HAs logs

Logger: homeassistant.components.websocket_api.http.connection
Source: custom_components/omnilogic/switch.py:235
Integration: Home Assistant WebSocket API (documentation, issues)
First occurred: 10:49:04 AM (4 occurrences)
Last logged: 10:58:31 AM

[140039323217200] Cannot set speed on a non-variable speed pump.
[140039998787696] Cannot set speed on a non-variable speed pump.
Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/components/websocket_api/commands.py", line 193, in handle_call_service
    await hass.services.async_call(
  File "/usr/src/homeassistant/homeassistant/core.py", line 1704, in async_call
    task.result()
  File "/usr/src/homeassistant/homeassistant/core.py", line 1741, in _execute_service
    await cast(Callable[[ServiceCall], Awaitable[None]], handler.job.target)(
  File "/usr/src/homeassistant/homeassistant/helpers/entity_platform.py", line 697, in handle_service
    await service.entity_service_call(
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 680, in entity_service_call
    future.result()  # pop exception if have
  File "/usr/src/homeassistant/homeassistant/helpers/entity.py", line 964, in async_request_call
    await coro
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 717, in _handle_entity_call
    await result
  File "/config/custom_components/omnilogic/switch.py", line 235, in async_set_speed
    raise OmniLogicException("Cannot set speed on a non-variable speed pump.")
omnilogic.OmniLogicException: Cannot set speed on a non-variable speed pump.

I'm not sure if it's caused by the pump type being not SINGLE as mentioned in the switch code (seen below), or something going out of sync along the way. For reference, here's the pump in use - TriStar VS 950 Omni https://github.com/djtimca/haomnilogic/blob/192561d3e7992799a92699199ee8227727dc6d13/custom_components/omnilogic/switch.py#L214-L235

If there's anything else I can include to help or troubleshoot, just let me know!

djtimca commented 2 years ago

Thanks @N3rdP1um23 - this is a good summary. I definitely have to fix the exception on the end of this.

It does appear that your pump is reporting as a single speed pump, but not sure why.

Can you go to: https://replit.com/@djtimca/OmniTesting

Hit "Run" at the top. Then enter your login/pass (not email address) and it will pull down the telemetry for your pool for me to review. (No credentials are saved, just the telemetry from the pool). From there I can hopefully see why your pump is showing as single speed (or what else is wrong).

Once you run it, look for a file in the files list called 'output_116_YOURUSERNAME_telemetry.json' and post it back here as a code block.

Can you also post separately what your service call looks like for those buttons?

Thanks!

N3rdP1um23 commented 2 years ago

No problem at all! Sure! Below is the requested information!

[
  {
    "systemId": "REDACTED",
    "statusVersion": "9",
    "airTemp": "67",
    "status": "2",
    "state": "1",
    "configUpdatedTime": "2022-06-06T21:36:05.067Z",
    "datetime": "2022-06-07T14:38:53.976",
    "Relays": [],
    "BOWS": [
      {
        "systemId": "1",
        "flow": "255",
        "waterTemp": "-1",
        "Name": "Pool",
        "Supports-Spillover": "no",
        "Filter": {
          "systemId": "2",
          "valvePosition": "1",
          "filterSpeed": "0",
          "filterState": "0",
          "lastSpeed": "75",
          "Name": "Filter Pump",
          "Shared-Type": "BOW_NO_EQUIPMENT_SHARED",
          "Filter-Type": "FMT_VARIABLE_SPEED_PUMP",
          "Max-Pump-Speed": "100",
          "Min-Pump-Speed": "18",
          "Max-Pump-RPM": "3450",
          "Min-Pump-RPM": "600",
          "Priming-Enabled": "yes",
          "Alarms": []
        },
        "VirtualHeater": {
          "systemId": "3",
          "Current-Set-Point": "75",
          "enable": "yes"
        },
        "Heater": {
          "systemId": "4",
          "heaterState": "0",
          "enable": "yes",
          "Shared-Type": "BOW_NO_EQUIPMENT_SHARED",
          "Operation": {
            "VirtualHeater": {
              "System-Id": "4",
              "Name": "Gas Heater",
              "Type": "PET_HEATER",
              "Heater-Type": "HTR_GAS",
              "Enabled": "yes",
              "Priority": "HTR_PRIORITY_1",
              "Run-For-Priority": "HTR_MAINTAINS_PRIORITY_FOR_AS_LONG_AS_VALID",
              "Shared-Equipment-System-ID": "-1",
              "Current-Set-Point": "75",
              "Max-Water-Temp": "104",
              "Min-Settable-Water-Temp": "55",
              "Max-Settable-Water-Temp": "104",
              "enable": "yes",
              "systemId": "3"
            }
          },
          "Name": "Gas Heater",
          "Alarms": []
        },
        "Chlorinator": {
          "systemId": "9",
          "operatingMode": "1",
          "Timed-Percent": "40",
          "scMode": "0",
          "chlrError": "0",
          "chlrAlert": "2048",
          "avgSaltLevel": "3500",
          "instantSaltLevel": "0",
          "status": "2",
          "Name": "Chlorinator",
          "Shared-Type": "BOW_NO_EQUIPMENT_SHARED",
          "Operation": [
            {
              "System-Id": "10",
              "Name": "Chlorinator1",
              "Type": "PET_CHLORINATOR",
              "Chlorinator-Type": "CHLOR_TYPE_AQUA_RITE",
              "Enabled": "yes"
            }
          ],
          "Alarms": []
        },
        "CSAD": {
          "systemId": "0",
          "ph": "",
          "orp": "",
          "status": "0",
          "mode": "0",
          "Alarms": []
        },
        "Lights": [
          {
            "systemId": "5",
            "lightState": "0",
            "currentShow": "0",
            "Name": "Lights",
            "Type": "COLOR_LOGIC_UCL",
            "V2": "no",
            "Alarms": []
          }
        ],
        "Relays": [],
        "Pumps": [
          {
            "systemId": "6",
            "pumpState": "1",
            "pumpSpeed": "100",
            "lastSpeed": "100",
            "Name": "InFloor Heat",
            "Type": "PMP_SINGLE_SPEED",
            "Function": "PMP_ACCESSORY",
            "Min-Pump-Speed": "18",
            "Max-Pump-Speed": "100",
            "Alarms": []
          }
        ],
        "Heaters": [
          {
            "systemId": "4",
            "heaterState": "0",
            "enable": "yes",
            "Shared-Type": "BOW_NO_EQUIPMENT_SHARED",
            "Operation": {
              "VirtualHeater": {
                "System-Id": "4",
                "Name": "Gas Heater",
                "Type": "PET_HEATER",
                "Heater-Type": "HTR_GAS",
                "Enabled": "yes",
                "Priority": "HTR_PRIORITY_1",
                "Run-For-Priority": "HTR_MAINTAINS_PRIORITY_FOR_AS_LONG_AS_VALID",
                "Shared-Equipment-System-ID": "-1",
                "Current-Set-Point": "75",
                "Max-Water-Temp": "104",
                "Min-Settable-Water-Temp": "55",
                "Max-Settable-Water-Temp": "104",
                "enable": "yes",
                "systemId": "3"
              }
            },
            "Name": "Gas Heater",
            "Alarms": []
          }
        ]
      }
    ],
    "BackyardName": "REDACTED",
    "Msp-Vsp-Speed-Format": "Percent",
    "Msp-Time-Format": "24 Hour Format",
    "Units": "Metric",
    "Msp-Chlor-Display": "Salt",
    "Msp-Language": "English",
    "Unit-of-Measurement": "Metric",
    "Alarms": [
      {
        "BowID": "0",
        "EquipmentID": "10",
        "Resource_Msg_Id": "77",
        "Severity": "1",
        "Parameter1": "Chlorinator1",
        "Parameter2": "none",
        "Valid": "0",
        "Clearable": "1",
        "Message": "CLEAN T-CELL Chlorinator1",
        "Comment": "Cell needs cleaning"
      }
    ],
    "Unit-of-Temperature": "UNITS_FAHRENHEIT"
  }
]

My horizontal stack of buttons, looks like this

type: horizontal-stack
cards:
  - show_name: true
    show_icon: true
    type: button
    tap_action:
      action: call-service
      service: omnilogic.set_pump_speed
      data:
        speed: 25
      target:
        area_id: pool
        entity_id: switch.pool_filter_pump
    entity: ''
    icon: mdi:speedometer-slow
    hold_action:
      action: none
    name: 25%
    show_state: false
    icon_height: 50px
  - show_name: true
    show_icon: true
    type: button
    tap_action:
      action: call-service
      service: omnilogic.set_pump_speed
      data:
        speed: 50
      target:
        area_id: pool
        entity_id: switch.pool_filter_pump
    entity: ''
    icon: mdi:speedometer-medium
    hold_action:
      action: none
    name: 50%
    show_state: false
    icon_height: 50px
  - show_name: true
    show_icon: true
    type: button
    tap_action:
      action: call-service
      service: omnilogic.set_pump_speed
      data:
        speed: 75
      target:
        area_id: pool
        entity_id: switch.pool_filter_pump
    entity: ''
    icon: mdi:speedometer
    hold_action:
      action: none
    name: 75%
    show_state: false
    icon_height: 50px

As a side note, for replit, could I make a suggestion or two? Would it be possible to use a hashed version of the username/execution time? Just thinking as the username could be something personal or an email address in some cases. As an example

import hashlib
from datetime import datetime

file_name_hash = hashlib.sha224(omni_username.encode() + str(datetime.now().timestamp()).encode()).hexdigest()[0:10]
file_name = "output_116_" + file_name_hash + "_telemetry.json"

# f = open("output_116_" + omni_username + "_telemetry.json", "w") ---- previous
f = open(file_name, "w")

print("Your telemetry results can be found in the following file... " + file_name)

And last one, zero out or replace the BackyardName and systemId for similar reasons? May save you from having to clear the files periodically as well haha Just a thought though, no worries at all if not ๐Ÿ™‚

djtimca commented 2 years ago

@N3rdP1um23 great suggestions on the Replit - I've added the hashing and automatically redact the SystemID and BackyardName now. Thanks!

I'm going to guess that the error is related to having a variable speed filter pump and a single speed pump for infloor heating. For some reason I must be trying to hit both when the service is called. Will do some digging and hopefully have a fix out tomorrow. Thanks!

N3rdP1um23 commented 2 years ago

Oh, awesome and no problem at all!! :)

Oh yeah, I did notice that, and it did in fact look off haha It's setup as a relay to control a circulation pump (manual on/off at a set schedule). Though now that I'm looking at it more, for some reason it's coming up as another pump from the API ๐Ÿค” That's odd lol

djtimca commented 2 years ago

I've got an update coming shortly which will require entity_id for the services, but something jumped out at me that might be causing your issue:

- show_name: true
    show_icon: true
    type: button
    tap_action:
      action: call-service
      service: omnilogic.set_pump_speed
      data:
        speed: 50
      target:
        area_id: pool
        entity_id: switch.pool_filter_pump
    entity: ''
    icon: mdi:speedometer-medium
    hold_action:
      action: none
    name: 50%
    show_state: false
    icon_height: 50px

You have targeted both an area_id and entity_id on the buttons. I think that both your pumps likely are assigned to the pool area, so Home Assistant may be calling the service against both.

Remove the area_id from the target section and see if that makes the problem go away.

N3rdP1um23 commented 2 years ago

Thanks for the update! I've tested it out and it worked! However, with a slight issue. I clicked on the 25% speed button and nothing happened, some of the entities on the dashboard went unavailable and then came back and finally set the pump speed to 25%.

Looking at the logs, I can see the following

This error originated from a custom integration.

Logger: custom_components.omnilogic.common
Source: helpers/update_coordinator.py:197
Integration: Hayward Omnilogic
First occurred: June 8, 2022 at 11:28:20 PM (156 occurrences)
Last logged: 10:04:02 AM

Timeout fetching Omnilogic data

Then due to the entity being unavailable, a couple of my automations failed

Logger: homeassistant.components.automation.update_pool_pump_speed_slider
Source: helpers/script.py:1718
Integration: Automation (documentation, issues)
First occurred: June 8, 2022 at 11:28:20 PM (314 occurrences)
Last logged: 10:04:02 AM

Update Pool Pump Speed Slider: Error executing script. Error for call_service at pos 1: Error rendering data template: ValueError: Template error: int got invalid input 'unavailable' when rendering template '{{ states.sensor.pool_filter_pump_speed.state | int }}' but no default was specified
Update Pool Pump Speed Slider: Error executing script. Invalid data for call_service at pos 1: Invalid value for input_number.pool_pump_speed: 0.0 (range 18.0 - 100.0)
Logger: homeassistant.components.automation.update_pool_pump_speed_slider
Source: components/automation/__init__.py:525
Integration: Automation (documentation, issues)
First occurred: June 8, 2022 at 11:28:20 PM (314 occurrences)
Last logged: 10:04:02 AM

Error while executing automation automation.update_pool_pump_speed_slider: Error rendering data template: ValueError: Template error: int got invalid input 'unavailable' when rendering template '{{ states.sensor.pool_filter_pump_speed.state | int }}' but no default was specified
Error while executing automation automation.update_pool_pump_speed_slider: Invalid value for input_number.pool_pump_speed: 0.0 (range 18.0 - 100.0)

Could this possibly be due to - https://github.com/djtimca/haomnilogic/releases/tag/1.0.9


Sure enough, I've tried it out more and it's working without issue ๐Ÿ˜†

djtimca commented 2 years ago

@N3rdP1um23 it does appear that the first set of errors is related to the entity being unavailable. I have some more work clearly to do on that. For whatever reason the Omnilogic API seems to be timing out way more often than it used to so I'll need to find a way to keep the last pull if a timeout happens.

I'll close this one and open a new issue for timeouts.

N3rdP1um23 commented 2 years ago

Aww man that's a bummer. Too bad they didn't have a local API ๐Ÿ˜ Though thanks again for all the support and catching me setting the area!

Take your time and enjoy the weekend in the pool though haha ๐Ÿ™‚

djtimca commented 2 years ago

@N3rdP1um23 they do have a local API - but we found out about it after everything was built.

It is definitely on the list of things I would like to improve when I have significantly more time... based on the build of the cloud version it will take a while to decipher what the local API spits out!

N3rdP1um23 commented 2 years ago

Oh hey that's awesome and it always works that way haha

No worries at all! I totally understand and do take your time! Do you have any additional information on it? I wouldn't mind looking into it and seeing what's up ๐Ÿ™‚

djtimca commented 2 years ago

I don't unfortunately - I saw the documentation once, but no idea where I put it. Will do some searching to see if I can track it down.