mirror of
https://github.com/home-assistant/core
synced 2024-08-02 23:40:32 +02:00
Fix HomeKit requests with hvac mode and temperature in the same call (#56239)
This commit is contained in:
parent
aaadd42539
commit
7524daad86
@ -245,7 +245,7 @@ class Thermostat(HomeAccessory):
|
||||
def _set_chars(self, char_values):
|
||||
_LOGGER.debug("Thermostat _set_chars: %s", char_values)
|
||||
events = []
|
||||
params = {}
|
||||
params = {ATTR_ENTITY_ID: self.entity_id}
|
||||
service = None
|
||||
state = self.hass.states.get(self.entity_id)
|
||||
features = state.attributes.get(ATTR_SUPPORTED_FEATURES, 0)
|
||||
@ -285,12 +285,20 @@ class Thermostat(HomeAccessory):
|
||||
target_hc = hc_fallback
|
||||
break
|
||||
|
||||
service = SERVICE_SET_HVAC_MODE_THERMOSTAT
|
||||
hass_value = self.hc_homekit_to_hass[target_hc]
|
||||
params = {ATTR_HVAC_MODE: hass_value}
|
||||
params[ATTR_HVAC_MODE] = self.hc_homekit_to_hass[target_hc]
|
||||
events.append(
|
||||
f"{CHAR_TARGET_HEATING_COOLING} to {char_values[CHAR_TARGET_HEATING_COOLING]}"
|
||||
)
|
||||
# Many integrations do not actually implement `hvac_mode` for the
|
||||
# `SERVICE_SET_TEMPERATURE_THERMOSTAT` service so we made a call to
|
||||
# `SERVICE_SET_HVAC_MODE_THERMOSTAT` before calling `SERVICE_SET_TEMPERATURE_THERMOSTAT`
|
||||
# to ensure the device is in the right mode before setting the temp.
|
||||
self.async_call_service(
|
||||
DOMAIN_CLIMATE,
|
||||
SERVICE_SET_HVAC_MODE_THERMOSTAT,
|
||||
params.copy(),
|
||||
", ".join(events),
|
||||
)
|
||||
|
||||
if CHAR_TARGET_TEMPERATURE in char_values:
|
||||
hc_target_temp = char_values[CHAR_TARGET_TEMPERATURE]
|
||||
@ -357,7 +365,6 @@ class Thermostat(HomeAccessory):
|
||||
)
|
||||
|
||||
if service:
|
||||
params[ATTR_ENTITY_ID] = self.entity_id
|
||||
self.async_call_service(
|
||||
DOMAIN_CLIMATE,
|
||||
service,
|
||||
|
@ -560,6 +560,119 @@ async def test_thermostat_auto(hass, hk_driver, events):
|
||||
)
|
||||
|
||||
|
||||
async def test_thermostat_mode_and_temp_change(hass, hk_driver, events):
|
||||
"""Test if accessory where the mode and temp change in the same call."""
|
||||
entity_id = "climate.test"
|
||||
|
||||
# support_auto = True
|
||||
hass.states.async_set(
|
||||
entity_id,
|
||||
HVAC_MODE_OFF,
|
||||
{
|
||||
ATTR_SUPPORTED_FEATURES: SUPPORT_TARGET_TEMPERATURE
|
||||
| SUPPORT_TARGET_TEMPERATURE_RANGE,
|
||||
ATTR_HVAC_MODES: [
|
||||
HVAC_MODE_HEAT,
|
||||
HVAC_MODE_HEAT_COOL,
|
||||
HVAC_MODE_FAN_ONLY,
|
||||
HVAC_MODE_COOL,
|
||||
HVAC_MODE_OFF,
|
||||
HVAC_MODE_AUTO,
|
||||
],
|
||||
},
|
||||
)
|
||||
await hass.async_block_till_done()
|
||||
acc = Thermostat(hass, hk_driver, "Climate", entity_id, 1, None)
|
||||
hk_driver.add_accessory(acc)
|
||||
|
||||
await acc.run()
|
||||
await hass.async_block_till_done()
|
||||
|
||||
assert acc.char_cooling_thresh_temp.value == 23.0
|
||||
assert acc.char_heating_thresh_temp.value == 19.0
|
||||
|
||||
assert acc.char_cooling_thresh_temp.properties[PROP_MAX_VALUE] == DEFAULT_MAX_TEMP
|
||||
assert acc.char_cooling_thresh_temp.properties[PROP_MIN_VALUE] == 7.0
|
||||
assert acc.char_cooling_thresh_temp.properties[PROP_MIN_STEP] == 0.1
|
||||
assert acc.char_heating_thresh_temp.properties[PROP_MAX_VALUE] == DEFAULT_MAX_TEMP
|
||||
assert acc.char_heating_thresh_temp.properties[PROP_MIN_VALUE] == 7.0
|
||||
assert acc.char_heating_thresh_temp.properties[PROP_MIN_STEP] == 0.1
|
||||
|
||||
hass.states.async_set(
|
||||
entity_id,
|
||||
HVAC_MODE_COOL,
|
||||
{
|
||||
ATTR_TARGET_TEMP_HIGH: 23.0,
|
||||
ATTR_TARGET_TEMP_LOW: 19.0,
|
||||
ATTR_CURRENT_TEMPERATURE: 21.0,
|
||||
ATTR_HVAC_ACTION: CURRENT_HVAC_COOL,
|
||||
ATTR_HVAC_MODES: [
|
||||
HVAC_MODE_HEAT,
|
||||
HVAC_MODE_HEAT_COOL,
|
||||
HVAC_MODE_FAN_ONLY,
|
||||
HVAC_MODE_COOL,
|
||||
HVAC_MODE_OFF,
|
||||
HVAC_MODE_AUTO,
|
||||
],
|
||||
},
|
||||
)
|
||||
await hass.async_block_till_done()
|
||||
assert acc.char_heating_thresh_temp.value == 19.0
|
||||
assert acc.char_cooling_thresh_temp.value == 23.0
|
||||
assert acc.char_current_heat_cool.value == HC_HEAT_COOL_COOL
|
||||
assert acc.char_target_heat_cool.value == HC_HEAT_COOL_COOL
|
||||
assert acc.char_current_temp.value == 21.0
|
||||
assert acc.char_display_units.value == 0
|
||||
|
||||
# Set from HomeKit
|
||||
call_set_temperature = async_mock_service(hass, DOMAIN_CLIMATE, "set_temperature")
|
||||
call_set_hvac_mode = async_mock_service(hass, DOMAIN_CLIMATE, "set_hvac_mode")
|
||||
|
||||
char_heating_thresh_temp_iid = acc.char_heating_thresh_temp.to_HAP()[HAP_REPR_IID]
|
||||
char_cooling_thresh_temp_iid = acc.char_cooling_thresh_temp.to_HAP()[HAP_REPR_IID]
|
||||
char_target_heat_cool_iid = acc.char_target_heat_cool.to_HAP()[HAP_REPR_IID]
|
||||
|
||||
hk_driver.set_characteristics(
|
||||
{
|
||||
HAP_REPR_CHARS: [
|
||||
{
|
||||
HAP_REPR_AID: acc.aid,
|
||||
HAP_REPR_IID: char_heating_thresh_temp_iid,
|
||||
HAP_REPR_VALUE: 20.0,
|
||||
},
|
||||
{
|
||||
HAP_REPR_AID: acc.aid,
|
||||
HAP_REPR_IID: char_cooling_thresh_temp_iid,
|
||||
HAP_REPR_VALUE: 25.0,
|
||||
},
|
||||
{
|
||||
HAP_REPR_AID: acc.aid,
|
||||
HAP_REPR_IID: char_target_heat_cool_iid,
|
||||
HAP_REPR_VALUE: HC_HEAT_COOL_AUTO,
|
||||
},
|
||||
]
|
||||
},
|
||||
"mock_addr",
|
||||
)
|
||||
|
||||
await hass.async_block_till_done()
|
||||
assert call_set_hvac_mode[0]
|
||||
assert call_set_hvac_mode[0].data[ATTR_ENTITY_ID] == entity_id
|
||||
assert call_set_hvac_mode[0].data[ATTR_HVAC_MODE] == HVAC_MODE_HEAT_COOL
|
||||
assert call_set_temperature[0]
|
||||
assert call_set_temperature[0].data[ATTR_ENTITY_ID] == entity_id
|
||||
assert call_set_temperature[0].data[ATTR_TARGET_TEMP_LOW] == 20.0
|
||||
assert call_set_temperature[0].data[ATTR_TARGET_TEMP_HIGH] == 25.0
|
||||
assert acc.char_heating_thresh_temp.value == 20.0
|
||||
assert acc.char_cooling_thresh_temp.value == 25.0
|
||||
assert len(events) == 2
|
||||
assert events[-2].data[ATTR_VALUE] == "TargetHeatingCoolingState to 3"
|
||||
assert (
|
||||
events[-1].data[ATTR_VALUE]
|
||||
== "TargetHeatingCoolingState to 3, CoolingThresholdTemperature to 25.0°C, HeatingThresholdTemperature to 20.0°C"
|
||||
)
|
||||
|
||||
|
||||
async def test_thermostat_humidity(hass, hk_driver, events):
|
||||
"""Test if accessory and HA are updated accordingly with humidity."""
|
||||
entity_id = "climate.test"
|
||||
|
Loading…
Reference in New Issue
Block a user