home-assistant / core

:house_with_garden: Open source home automation that puts local control and privacy first.
https://www.home-assistant.io
Apache License 2.0
73.3k stars 30.61k forks source link

Nexia integration accurately reads humidity setpoint but cannot change it (humidifier, not de-humidifier, is installed) #52693

Closed joshlawless closed 3 years ago

joshlawless commented 3 years ago

The problem

I have an American Standard XL824 thermostat integrated with homeassistant via the Nexia integration, and it works reasonably well (when the asair.com server doesn't happen to be crashing). One thing I recently discovered, although it's the wrong time of the year to worry about it, is that the built-in humidifier (n.b., NOT a de-humidifier, we live in a desert) doesn't work with the integration.

If I go to asair.com I can change a humidity target and that change is (eventually, when asair.com feels like it) reflected in the entity. But when I attempt to change the humidity target in the more-info panel, or via a service call, I get an error message complaining that my thermostat doesn't support DE-humidifying. I agree, it doesn't, but I would like to be able to set a humidity target in the winter so we don't all dry up and blow away.

websocket_api script: Error executing script. Unexpected error for call_service at pos 1: This thermostat does not support dehumidifying.
Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 371, in _async_step
    await getattr(self, handler)()
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 571, in _async_call_service_step
    await service_task
  File "/usr/src/homeassistant/homeassistant/core.py", line 1491, in async_call
    task.result()
  File "/usr/src/homeassistant/homeassistant/core.py", line 1526, in _execute_service
    await handler.job.target(service_call)
  File "/usr/src/homeassistant/homeassistant/helpers/entity_component.py", line 213, in handle_service
    await self.hass.helpers.service.entity_service_call(
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 658, in entity_service_call
    future.result()  # pop exception if have
  File "/usr/src/homeassistant/homeassistant/helpers/entity.py", line 811, in async_request_call
    await coro
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 695, in _handle_entity_call
    await result
  File "/usr/src/homeassistant/homeassistant/components/climate/__init__.py", line 447, in async_set_humidity
    await self.hass.async_add_executor_job(self.set_humidity, humidity)
  File "/usr/local/lib/python3.9/concurrent/futures/thread.py", line 52, in run
    result = self.fn(*self.args, **self.kwargs)
  File "/usr/src/homeassistant/homeassistant/components/nexia/climate.py", line 206, in set_humidity
    self._thermostat.set_dehumidify_setpoint(humidity / 100.0)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 520, in set_dehumidify_setpoint
    self.set_humidity_setpoints(dehumidify_setpoint=dehumidify_setpoint)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 472, in set_humidity_setpoints
    raise SystemError("This thermostat does not support dehumidifying.")
SystemError: This thermostat does not support dehumidifying.

What is version of Home Assistant Core has the issue?

2021.7.0

What was the last working version of Home Assistant Core?

No response

What type of installation are you running?

Home Assistant Container

Integration causing the issue

Nexia/American Standard

Link to integration documentation on our website

https://www.home-assistant.io/integrations/nexia/

Example YAML snippet

No response

Anything in the logs that might be useful for us?

Logger: homeassistant.helpers.script.websocket_api_script
Source: components/nexia/climate.py:206 
First occurred: 5:08:04 PM (1 occurrences) 
Last logged: 5:08:04 PM

websocket_api script: Error executing script. Unexpected error for call_service at pos 1: This thermostat does not support dehumidifying.
Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 371, in _async_step
    await getattr(self, handler)()
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 571, in _async_call_service_step
    await service_task
  File "/usr/src/homeassistant/homeassistant/core.py", line 1491, in async_call
    task.result()
  File "/usr/src/homeassistant/homeassistant/core.py", line 1526, in _execute_service
    await handler.job.target(service_call)
  File "/usr/src/homeassistant/homeassistant/helpers/entity_component.py", line 213, in handle_service
    await self.hass.helpers.service.entity_service_call(
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 658, in entity_service_call
    future.result()  # pop exception if have
  File "/usr/src/homeassistant/homeassistant/helpers/entity.py", line 811, in async_request_call
    await coro
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 695, in _handle_entity_call
    await result
  File "/usr/src/homeassistant/homeassistant/components/climate/__init__.py", line 447, in async_set_humidity
    await self.hass.async_add_executor_job(self.set_humidity, humidity)
  File "/usr/local/lib/python3.9/concurrent/futures/thread.py", line 52, in run
    result = self.fn(*self.args, **self.kwargs)
  File "/usr/src/homeassistant/homeassistant/components/nexia/climate.py", line 206, in set_humidity
    self._thermostat.set_dehumidify_setpoint(humidity / 100.0)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 520, in set_dehumidify_setpoint
    self.set_humidity_setpoints(dehumidify_setpoint=dehumidify_setpoint)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 472, in set_humidity_setpoints
    raise SystemError("This thermostat does not support dehumidifying.")
SystemError: This thermostat does not support dehumidifying.

Additional information

No response

probot-home-assistant[bot] commented 3 years ago

nexia documentation nexia source (message by IssueLinks)

bdraco commented 3 years ago

Can you provide a dump of what the mobile app does when you change the humidity using Charles proxy for iPhone?

joshlawless commented 3 years ago

Here you go:

Output of "Copy cURL" from the POST:

curl -H "Host: www.mynexia.com" -H "content-type: application/json; charset=utf-8" -H "accept: application/json" -H "accept-language: en-us" -H "x-apikey: de7bdea75e3964e3720db7c75fa39b89" -H "x-mobileid: 3314011" -H "origin: http://localhost:4401" -H "x-associatedbrand: asair" -H "user-agent: Mozilla/5.0 (iPhone; CPU iPhone OS 14_6 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Mobile/15E148" -H "referer: http://localhost:4401/" -H "x-appversion: 5.16.0" --data-binary "{\"value\":\"0.4\"}" --compressed "https://www.mynexia.com/mobile/xxl_thermostats/3269606/humidify"

Output of "Raw" data from viewing Request:

:method: POST
:scheme: https
:path: /mobile/xxl_thermostats/3269606/humidify
:authority: www.mynexia.com
content-type: application/json; charset=utf-8
accept: application/json
accept-language: en-us
x-apikey: [snip]
accept-encoding: gzip, deflate, br
x-mobileid: 3314011
origin: http://localhost:4401
content-length: 15
x-associatedbrand: asair
user-agent: Mozilla/5.0 (iPhone; CPU iPhone OS 14_6 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Mobile/15E148
referer: http://localhost:4401/
x-appversion: 5.16.0

{"value":"0.4"}

Output of "Copy Response" from the POST:

{
  "success": true,
  "error": null,
  "result": {"id":3269606,"name":"Downstairs Thermostat","name_editable":true,"features":[{"name":"advanced_info","items":[{"type":"label_value","label":"Model","value":"XL824"},{"type":"label_value","label":"AUID","value":"01745698"},{"type":"label_value","label":"Firmware Build Number","value":"1591678507"},{"type":"label_value","label":"Firmware Build Date","value":"2020-06-09 04:55:07 UTC"},{"type":"label_value","label":"Firmware Version","value":"5.9.2"},{"type":"label_value","label":"On Board Device","value":"Bridge"}]},{"name":"thermostat","temperature":73,"status":"Waiting...","status_icon":null,"actions":{"set_cool_setpoint":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/setpoints"}},"setpoint_delta":3,"scale":"f","setpoint_increment":1.0,"setpoint_heat_min":55,"setpoint_heat_max":90,"setpoint_cool_min":60,"setpoint_cool_max":99,"setpoint_cool":73,"system_status":"Waiting..."},{"name":"connection","signal_strength":"unknown","is_connected":true},{"name":"dealer_contact_info","has_dealer_identifier":true,"actions":{"request_current_dealer_info":{"method":"GET","href":"https://www.mynexia.com/mobile/dealers/2089066928"},"request_dealers_by_zip":{"method":"POST","href":"https://www.mynexia.com/mobile/dealers/3269606/search"}}},{"name":"thermostat_mode","label":"System Mode","value":"COOL","display_value":"Cooling","options":[{"id":"thermostat_mode","label":"System Mode","value":"thermostat_mode","header":true},{"value":"AUTO","label":"Auto"},{"value":"COOL","label":"Cooling"},{"value":"HEAT","label":"Heating"},{"value":"OFF","label":"Off"}],"actions":{"update_thermostat_mode":{"method":"POST","href":"https://www.mynexia.com/mobile/xxl_zones/83957146/zone_mode"}}},{"name":"thermostat_run_mode","label":"Run Mode","options":[{"id":"thermostat_run_mode","label":"Run Mode","value":"thermostat_run_mode","header":true},{"id":"info_text","label":"Follow or override the schedule.","value":"info_text","info":true},{"value":"permanent_hold","label":"Permanent Hold"},{"value":"run_schedule","label":"Run Schedule"}],"value":"permanent_hold","display_value":"Hold","actions":{"update_thermostat_run_mode":{"method":"POST","href":"https://www.mynexia.com/mobile/xxl_zones/83957146/run_mode"}}},{"name":"room_iq_sensors","sensors":[{"id":16302685,"name":"Downstairs Thermostat","icon":{"name":"room_iq_onboard","modifiers":[]},"type":"thermostat","serial_number":"NativeIDTUniqueID","weight":0.33,"temperature":74,"temperature_valid":true,"humidity":48,"humidity_valid":true,"has_online":false,"has_battery":false},{"id":16302688,"name":"Office","icon":{"name":"room_iq_wireless","modifiers":[]},"type":"930","serial_number":"2033R2AL6X","weight":0.33,"temperature":72,"temperature_valid":true,"humidity":48,"humidity_valid":true,"has_online":true,"connected":true,"has_battery":true,"battery_level":100,"battery_low":false,"battery_valid":true},{"id":16302691,"name":"Master","icon":{"name":"room_iq_wireless","modifiers":[]},"type":"930","serial_number":"1829R2ASGX","weight":0.33,"temperature":73,"temperature_valid":true,"humidity":50,"humidity_valid":true,"has_online":true,"connected":true,"has_battery":true,"battery_level":100,"battery_low":false,"battery_valid":true}],"should_show":true,"actions":{"request_current_state":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/request_current_sensor_state"},"update_active_sensors":{"method":"POST","href":"https://www.mynexia.com/mobile/xxl_zones/83957146/update_active_sensors"}}},{"name":"thermostat_fan_mode","label":"Fan Mode","options":[{"id":"thermostat_fan_mode","label":"Fan Mode","value":"thermostat_fan_mode","header":true},{"value":"auto","label":"Auto"},{"value":"on","label":"On"},{"value":"circulate","label":"Circulate"}],"value":"on","display_value":"On","status_icon":{"name":"thermostat_fan_on","modifiers":[]},"actions":{"update_thermostat_fan_mode":{"method":"POST","href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/fan_mode"}}},{"name":"runtime_history","actions":{"get_runtime_history":{"method":"GET","href":"https://www.mynexia.com/mobile/runtime_history/3269606?report_type=daily"},"get_monthly_runtime_history":{"method":"GET","href":"https://www.mynexia.com/mobile/runtime_history/3269606?report_type=monthly"}}},{"name":"schedule","enabled":true,"max_period_name_length":10,"setpoint_increment":1,"collection_url":"https://www.mynexia.com/mobile/schedules?device_identifier=TraneXl824-3269606\u0026house_id=1653639","actions":{"get_active_schedule":{"href":"https://www.mynexia.com/mobile/thermostat_schedules/get_active_schedule?device_identifier=TraneXl824-3269606","method":"POST"},"set_active_schedule":{"href":"https://www.mynexia.com/mobile/thermostat_schedules/set_active_schedule?device_identifier=TraneXl824-3269606","method":"POST"},"get_default_schedule":{"href":"https://www.mynexia.com/mobile/thermostat_schedules/get_default_schedule?device_identifier=TraneXl824-3269606","method":"GET"},"enable_scheduling":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/scheduling_enabled","method":"POST","data":{"value":true}}},"can_add_remove_periods":true,"max_periods_per_day":6}],"icon":[{"name":"thermostat","modifiers":["temperature-73"]}],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606"},"nexia:history":{"href":"https://www.mynexia.com/mobile/houses/1653639/events?device_id=3269606"},"filter_events":{"href":"https://www.mynexia.com/mobile/houses/1653639/events/collection?sys_guid=6af336a9-5435-4379-960a-48862f544a25"}},"last_updated_at":"2021-07-08T08:29:12.000-06:00","settings":[{"type":"preset_selected","title":"Preset","current_value":0,"options":[{"value":0,"label":"None"},{"value":1,"label":"Home"},{"value":2,"label":"Away"},{"value":3,"label":"Sleep"}],"labels":["None","Home","Away","Sleep"],"values":[0,1,2,3],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/preset_selected"}}},{"type":"system_mode","title":"System Mode","current_value":"COOL","options":[{"value":"AUTO","label":"Auto"},{"value":"COOL","label":"Cooling"},{"value":"HEAT","label":"Heating"},{"value":"OFF","label":"Off"}],"labels":["Auto","Cooling","Heating","Off"],"values":["AUTO","COOL","HEAT","OFF"],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/zone_mode"}}},{"type":"run_mode","title":"Run Mode","current_value":"permanent_hold","options":[{"value":"permanent_hold","label":"Permanent Hold"},{"value":"run_schedule","label":"Run Schedule"}],"labels":["Permanent Hold","Run Schedule"],"values":["permanent_hold","run_schedule"],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/run_mode"}}},{"type":"scheduling_enabled","title":"Scheduling","current_value":true,"options":[{"value":true,"label":"ON"},{"value":false,"label":"OFF"}],"labels":["ON","OFF"],"values":[true,false],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/scheduling_enabled"}}},{"type":"fan_mode","title":"Fan Mode","current_value":"on","options":[{"value":"auto","label":"Auto"},{"value":"on","label":"On"},{"value":"circulate","label":"Circulate"}],"labels":["Auto","On","Circulate"],"values":["auto","on","circulate"],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/fan_mode"}}},{"type":"fan_speed","title":"Fan Speed","current_value":1.0,"options":[{"value":0.35,"label":"35%"},{"value":0.4,"label":"40%"},{"value":0.45,"label":"45%"},{"value":0.5,"label":"50%"},{"value":0.55,"label":"55%"},{"value":0.6,"label":"60%"},{"value":0.65,"label":"65%"},{"value":0.7,"label":"70%"},{"value":0.75,"label":"75%"},{"value":0.8,"label":"80%"},{"value":0.85,"label":"85%"},{"value":0.9,"label":"90%"},{"value":0.95,"label":"95%"},{"value":1.0,"label":"100%"}],"labels":["35%","40%","45%","50%","55%","60%","65%","70%","75%","80%","85%","90%","95%","100%"],"values":[0.35,0.4,0.45,0.5,0.55,0.6,0.65,0.7,0.75,0.8,0.85,0.9,0.95,1.0],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/fan_speed"}}},{"type":"fan_circulation_time","title":"Fan Circulation Time","current_value":30,"options":[{"value":10,"label":"10 minutes"},{"value":15,"label":"15 minutes"},{"value":20,"label":"20 minutes"},{"value":25,"label":"25 minutes"},{"value":30,"label":"30 minutes"},{"value":35,"label":"35 minutes"},{"value":40,"label":"40 minutes"},{"value":45,"label":"45 minutes"},{"value":50,"label":"50 minutes"},{"value":55,"label":"55 minutes"}],"labels":["10 minutes","15 minutes","20 minutes","25 minutes","30 minutes","35 minutes","40 minutes","45 minutes","50 minutes","55 minutes"],"values":[10,15,20,25,30,35,40,45,50,55],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/fan_circulation_time"}}},{"type":"air_cleaner_mode","title":"Air Cleaner Mode","current_value":"auto","options":[{"value":"auto","label":"Auto"},{"value":"quick","label":"Quick"},{"value":"allergy","label":"Allergy"}],"labels":["Auto","Quick","Allergy"],"values":["auto","quick","allergy"],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/air_cleaner_mode"}}},{"type":"humidify","title":"Heating Humidify Set Point","current_value":0.4,"options":[{"value":0.1,"label":"10%"},{"value":0.15,"label":"15%"},{"value":0.2,"label":"20%"},{"value":0.25,"label":"25%"},{"value":0.3,"label":"30%"},{"value":0.35,"label":"35%"},{"value":0.4,"label":"40%"},{"value":0.45,"label":"45%"}],"labels":["10%","15%","20%","25%","30%","35%","40%","45%"],"values":[0.1,0.15,0.2,0.25,0.3,0.35,0.4,0.45],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/humidify"}}},{"type":"scale","title":"Temperature Scale","current_value":"f","options":[{"value":"f","label":"F"},{"value":"c","label":"C"}],"labels":["F","C"],"values":["f","c"],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/scale"}}}],"status_secondary":null,"status_tertiary":null,"type":"xxl_thermostat","has_outdoor_temperature":true,"outdoor_temperature":"99","has_indoor_humidity":true,"connected":true,"indoor_humidity":"47","system_status":"Waiting...","delta":3,"manufacturer":"AmericanStandard","zones":[{"type":"xxl_zone","id":83957146,"name":"NativeZone","current_zone_mode":"COOL","temperature":73,"setpoints":{"heat":67,"cool":73},"operating_state":"","heating_setpoint":67,"cooling_setpoint":73,"zone_status":"","settings":[],"icon":{"name":"thermostat","modifiers":["temperature-73"]},"features":[{"name":"thermostat","temperature":73,"status":"","status_icon":null,"actions":{"set_cool_setpoint":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/setpoints"}},"setpoint_delta":3,"scale":"f","setpoint_increment":1.0,"setpoint_heat_min":55,"setpoint_heat_max":90,"setpoint_cool_min":60,"setpoint_cool_max":99,"setpoint_cool":73,"system_status":"Waiting..."},{"name":"connection","signal_strength":"unknown","is_connected":true},{"name":"dealer_contact_info","has_dealer_identifier":true,"actions":{"request_current_dealer_info":{"method":"GET","href":"https://www.mynexia.com/mobile/dealers/2089066928"},"request_dealers_by_zip":{"method":"POST","href":"https://www.mynexia.com/mobile/dealers/3269606/search"}}},{"name":"thermostat_mode","label":"System Mode","value":"COOL","display_value":"Cooling","options":[{"id":"thermostat_mode","label":"System Mode","value":"thermostat_mode","header":true},{"value":"AUTO","label":"Auto"},{"value":"COOL","label":"Cooling"},{"value":"HEAT","label":"Heating"},{"value":"OFF","label":"Off"}],"actions":{"update_thermostat_mode":{"method":"POST","href":"https://www.mynexia.com/mobile/xxl_zones/83957146/zone_mode"}}},{"name":"thermostat_run_mode","label":"Run Mode","options":[{"id":"thermostat_run_mode","label":"Run Mode","value":"thermostat_run_mode","header":true},{"id":"info_text","label":"Follow or override the schedule.","value":"info_text","info":true},{"value":"permanent_hold","label":"Permanent Hold"},{"value":"run_schedule","label":"Run Schedule"}],"value":"permanent_hold","display_value":"Hold","actions":{"update_thermostat_run_mode":{"method":"POST","href":"https://www.mynexia.com/mobile/xxl_zones/83957146/run_mode"}}},{"name":"room_iq_sensors","sensors":[{"id":16302685,"name":"Downstairs Thermostat","icon":{"name":"room_iq_onboard","modifiers":[]},"type":"thermostat","serial_number":"NativeIDTUniqueID","weight":0.33,"temperature":74,"temperature_valid":true,"humidity":48,"humidity_valid":true,"has_online":false,"has_battery":false},{"id":16302688,"name":"Office","icon":{"name":"room_iq_wireless","modifiers":[]},"type":"930","serial_number":"2033R2AL6X","weight":0.33,"temperature":72,"temperature_valid":true,"humidity":48,"humidity_valid":true,"has_online":true,"connected":true,"has_battery":true,"battery_level":100,"battery_low":false,"battery_valid":true},{"id":16302691,"name":"Master","icon":{"name":"room_iq_wireless","modifiers":[]},"type":"930","serial_number":"1829R2ASGX","weight":0.33,"temperature":73,"temperature_valid":true,"humidity":50,"humidity_valid":true,"has_online":true,"connected":true,"has_battery":true,"battery_level":100,"battery_low":false,"battery_valid":true}],"should_show":true,"actions":{"request_current_state":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/request_current_sensor_state"},"update_active_sensors":{"method":"POST","href":"https://www.mynexia.com/mobile/xxl_zones/83957146/update_active_sensors"}}},{"name":"schedule","enabled":true,"max_period_name_length":10,"setpoint_increment":1,"collection_url":"https://www.mynexia.com/mobile/schedules?device_identifier=XxlZone-83957146\u0026house_id=1653639","actions":{"get_active_schedule":{"href":"https://www.mynexia.com/mobile/thermostat_schedules/get_active_schedule?device_identifier=XxlZone-83957146","method":"POST"},"set_active_schedule":{"href":"https://www.mynexia.com/mobile/thermostat_schedules/set_active_schedule?device_identifier=XxlZone-83957146","method":"POST"},"get_default_schedule":{"href":"https://www.mynexia.com/mobile/thermostat_schedules/get_default_schedule?device_identifier=XxlZone-83957146","method":"GET"},"enable_scheduling":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146/scheduling_enabled","method":"POST","data":{"value":true}}},"can_add_remove_periods":true,"max_periods_per_day":6}],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_zones/83957146"}}}],"generic_input_sensors":[]}
}

Hope I got what you needed there.

joshlawless commented 3 years ago

.. for context, that was me using the app to adjust the humidity setpoint from 45% to 40%

bdraco commented 3 years ago

@joshlawless Can you give https://github.com/home-assistant/core/pull/52758 a shot?

You should be able to check it out and install it in /config/custom_components/nexia by adding any version key to manifest.json

joshlawless commented 3 years ago

Happy to try, but can you explain it to me like I'm incompetent? I'm guessing I need to download the contents of the https://github.com/bdraco/home-assistant/tree/nexia_humidify/homeassistant/components/nexia folder into a newly created /config/custom_components/nexia folder in my instance, then modify the manifest.json file ... somehow? Before restarting HA? Anything else to get HA to recognize it? Need to disable current Nexia integration first?

bdraco commented 3 years ago

Doing so will override the included integration.

manifest.json needs to look something like this (notice the extra version key)

{
  "domain": "nexia",
  "name": "Nexia/American Standard",
  "requirements": ["nexia==0.9.8"],
  "codeowners": ["@bdraco"],
  "documentation": "https://www.home-assistant.io/integrations/nexia",
  "config_flow": true,
  "dhcp": [
    {
      "hostname": "xl857-*",
      "macaddress": "000231*"
    }
  ],
  "iot_class": "cloud_polling",
  "version": "1.0.0"
}

That should be it after a restart.

joshlawless commented 3 years ago

So I did that, restarted, and still get an error trying to set humidity:

Logger: homeassistant.helpers.script.websocket_api_script
Source: components/nexia/climate.py:206 
First occurred: 9:31:07 AM (1 occurrences) 
Last logged: 9:31:07 AM

websocket_api script: Error executing script. Unexpected error for call_service at pos 1: This thermostat does not support dehumidifying.
Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 371, in _async_step
    await getattr(self, handler)()
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 571, in _async_call_service_step
    await service_task
  File "/usr/src/homeassistant/homeassistant/core.py", line 1491, in async_call
    task.result()
  File "/usr/src/homeassistant/homeassistant/core.py", line 1526, in _execute_service
    await handler.job.target(service_call)
  File "/usr/src/homeassistant/homeassistant/helpers/entity_component.py", line 213, in handle_service
    await self.hass.helpers.service.entity_service_call(
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 658, in entity_service_call
    future.result()  # pop exception if have
  File "/usr/src/homeassistant/homeassistant/helpers/entity.py", line 811, in async_request_call
    await coro
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 695, in _handle_entity_call
    await result
  File "/usr/src/homeassistant/homeassistant/components/climate/__init__.py", line 447, in async_set_humidity
    await self.hass.async_add_executor_job(self.set_humidity, humidity)
  File "/usr/local/lib/python3.9/concurrent/futures/thread.py", line 52, in run
    result = self.fn(*self.args, **self.kwargs)
  File "/usr/src/homeassistant/homeassistant/components/nexia/climate.py", line 206, in set_humidity
    self._thermostat.set_dehumidify_setpoint(humidity / 100.0)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 520, in set_dehumidify_setpoint
    self.set_humidity_setpoints(dehumidify_setpoint=dehumidify_setpoint)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 472, in set_humidity_setpoints
    raise SystemError("This thermostat does not support dehumidifying.")
SystemError: This thermostat does not support dehumidifying.

I am not sure that the custom_component is loaded, though -- in the integration page of the HA config, there is a cardboard box icon in the upper corner of the HACS integration which has a tooltip indicating "Provided by a custom integration" - no such icon appears next to the Nexia component (just the cloud icon). Is there a way to determine the version installed? Perhaps from a CLI inside the container?

bdraco commented 3 years ago

Its definitely not using the custom component as the trace has /usr/src/homeassistant/homeassistant/components/nexia/ instead of /config/custom_components/nexia

bdraco commented 3 years ago

It might be helpful to use https://github.com/alandtse/pr_custom_component

joshlawless commented 3 years ago

Well, I tried disabling the cloud nexia integration and restarting, no dice. Tried deleting the nexia integration and restarting, still no-go.

joshlawless commented 3 years ago

I've got the PR custom component integration installed, but it wants a pull request, not a URL like https://github.com/bdraco/home-assistant/tree/nexia_humidify/homeassistant/components/nexia -- is there a pull request I should use?

NVM, figure that part out -- https://github.com/home-assistant/core/pull/52758

Now, though, how do I get the Nexia component configured? The configure option for the integration just offers checkboxes to enable binary_sensor, sensor, and switch; there's nowhere to put nexia login credentials, etc.

Am I supposed to install this over the top of the cloud Nexia integration?

bdraco commented 3 years ago

The https://github.com/alandtse/pr_custom_component component will take care of installing it for you. The sensors it creates are about the state of the install

joshlawless commented 3 years ago

So I figured that all out, and am now able to set humidity from HA using the updated component. One problem: The asair.com site allows me to change humidity in 5% increments (i.e., to 10%, 15%, 20%, 25%, 30%, 35%, 40% or 45%). The input slider in the climate more-info panel in HA permits 1% increments from 35% to 65%. If I select a valid value with the input slider, the change is shortly reflected on asair.com. If I select an invalid value (easy to do, as it's a slider), then I trigger an error:

Logger: homeassistant.core
Source: custom_components/nexia/climate.py:209 
Integration: Custom Nexia PR#52758 
First occurred: 10:13:38 AM (1 occurrences) 
Last logged: 10:13:38 AM

Error executing service: <ServiceCall climate.set_humidity (c:a8109c01a7dedb1f024fd161fafdcbb0): humidity=39.0, entity_id=['climate.downstairs_thermostat_nativezone']>
Traceback (most recent call last):
  File "/usr/local/lib/python3.9/site-packages/urllib3/connectionpool.py", line 445, in _make_request
    six.raise_from(e, None)
  File "<string>", line 3, in raise_from
  File "/usr/local/lib/python3.9/site-packages/urllib3/connectionpool.py", line 440, in _make_request
    httplib_response = conn.getresponse()
  File "/usr/local/lib/python3.9/http/client.py", line 1345, in getresponse
    response.begin()
  File "/usr/local/lib/python3.9/http/client.py", line 307, in begin
    version, status, reason = self._read_status()
  File "/usr/local/lib/python3.9/http/client.py", line 268, in _read_status
    line = str(self.fp.readline(_MAXLINE + 1), "iso-8859-1")
  File "/usr/local/lib/python3.9/socket.py", line 704, in readinto
    return self._sock.recv_into(b)
  File "/usr/local/lib/python3.9/ssl.py", line 1241, in recv_into
    return self.read(nbytes, buffer)
  File "/usr/local/lib/python3.9/ssl.py", line 1099, in read
    return self._sslobj.read(len, buffer)
socket.timeout: The read operation timed out

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/usr/local/lib/python3.9/site-packages/requests/adapters.py", line 439, in send
    resp = conn.urlopen(
  File "/usr/local/lib/python3.9/site-packages/urllib3/connectionpool.py", line 755, in urlopen
    retries = retries.increment(
  File "/usr/local/lib/python3.9/site-packages/urllib3/util/retry.py", line 532, in increment
    raise six.reraise(type(error), error, _stacktrace)
  File "/usr/local/lib/python3.9/site-packages/urllib3/packages/six.py", line 770, in reraise
    raise value
  File "/usr/local/lib/python3.9/site-packages/urllib3/connectionpool.py", line 699, in urlopen
    httplib_response = self._make_request(
  File "/usr/local/lib/python3.9/site-packages/urllib3/connectionpool.py", line 447, in _make_request
    self._raise_timeout(err=e, url=url, timeout_value=read_timeout)
  File "/usr/local/lib/python3.9/site-packages/urllib3/connectionpool.py", line 336, in _raise_timeout
    raise ReadTimeoutError(
urllib3.exceptions.ReadTimeoutError: HTTPSConnectionPool(host='www.asairhome.com', port=443): Read timed out. (read timeout=20)

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/core.py", line 1507, in catch_exceptions
    await coro_or_task
  File "/usr/src/homeassistant/homeassistant/core.py", line 1526, in _execute_service
    await handler.job.target(service_call)
  File "/usr/src/homeassistant/homeassistant/helpers/entity_component.py", line 213, in handle_service
    await self.hass.helpers.service.entity_service_call(
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 658, in entity_service_call
    future.result()  # pop exception if have
  File "/usr/src/homeassistant/homeassistant/helpers/entity.py", line 811, in async_request_call
    await coro
  File "/usr/src/homeassistant/homeassistant/helpers/service.py", line 695, in _handle_entity_call
    await result
  File "/usr/src/homeassistant/homeassistant/components/climate/__init__.py", line 447, in async_set_humidity
    await self.hass.async_add_executor_job(self.set_humidity, humidity)
  File "/usr/local/lib/python3.9/concurrent/futures/thread.py", line 52, in run
    result = self.fn(*self.args, **self.kwargs)
  File "/config/custom_components/nexia/climate.py", line 209, in set_humidity
    self._thermostat.set_humidify_setpoint(humidity / 100.0)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 534, in set_humidify_setpoint
    self.set_humidity_setpoints(humidify_setpoint=humidify_setpoint)
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 512, in set_humidity_setpoints
    self._post_and_update_thermostat_json(
  File "/usr/local/lib/python3.9/site-packages/nexia/thermostat.py", line 665, in _post_and_update_thermostat_json
    response = self._nexia_home.post_url(url, payload)
  File "/usr/local/lib/python3.9/site-packages/nexia/home.py", line 145, in post_url
    response = self.session.post(
  File "/usr/local/lib/python3.9/site-packages/requests/sessions.py", line 590, in post
    return self.request('POST', url, data=data, json=json, **kwargs)
  File "/usr/local/lib/python3.9/site-packages/requests/sessions.py", line 542, in request
    resp = self.send(prep, **send_kwargs)
  File "/usr/local/lib/python3.9/site-packages/requests/sessions.py", line 655, in send
    r = adapter.send(request, **kwargs)
  File "/usr/local/lib/python3.9/site-packages/requests/adapters.py", line 529, in send
    raise ReadTimeout(e, request=request)
requests.exceptions.ReadTimeout: HTTPSConnectionPool(host='www.asairhome.com', port=443): Read timed out. (read timeout=20)
bdraco commented 3 years ago

Glad its working now 👍

The climate integration currently doesn't support setting a step size for humidity, only temperature.

https://developers.home-assistant.io/docs/core/entity/climate

If it ever does, we can set it to 5 but since that would require an architecture change to Home Assistant itself, this isn't something the nexia integration can do currently.

joshlawless commented 3 years ago

Can the min and max of the range be changed? I think it's currently set to the range Nexia uses for de-humidification (operative while cooling, based on the asair.com GUI), but that range is different for humidification (operative while heating).

In the image below, you can see screenshots of asair.com, where I have two XL824 thermostats registered (upstairs and downstairs). Only one has a humidifier installed. That one is on top, shows the label "heating" in the humidify menu, and lets me set the range in 5% increments from 10 to 45. The other doesn't have a humidifier or a de-humidifier, but shows the default dehumidification settings (the label is "cooling" in the humidify menu) and permits a range of 35% to 65% in 5% increments.
asair

bdraco commented 3 years ago
{"type":"humidify","title":"Heating Humidify Set Point","current_value":0.4,"options":[{"value":0.1,"label":"10%"},{"value":0.15,"label":"15%"},{"value":0.2,"label":"20%"},{"value":0.25,"label":"25%"},{"value":0.3,"label":"30%"},{"value":0.35,"label":"35%"},{"value":0.4,"label":"40%"},{"value":0.45,"label":"45%"}],"labels":["10%","15%","20%","25%","30%","35%","40%","45%"],"values":[0.1,0.15,0.2,0.25,0.3,0.35,0.4,0.45],"_links":{"self":{"href":"https://www.mynexia.com/mobile/xxl_thermostats/3269606/humidify"}}}

It looks like there is enough data in the json to figure out the limits