Skip to content

Commit

Permalink
Handle mains power for Matter appliances (#121023)
Browse files Browse the repository at this point in the history
  • Loading branch information
marcelveldt authored and frenck committed Jul 2, 2024
1 parent b3e833f commit 1fa6972
Show file tree
Hide file tree
Showing 4 changed files with 35 additions and 3 deletions.
7 changes: 7 additions & 0 deletions homeassistant/components/matter/climate.py
Original file line number Diff line number Diff line change
Expand Up @@ -227,6 +227,13 @@ def _update_from_device(self) -> None:
self._attr_current_temperature = self._get_temperature_in_degrees(
clusters.Thermostat.Attributes.LocalTemperature
)
if self.get_matter_attribute_value(clusters.OnOff.Attributes.OnOff) is False:
# special case: the appliance has a dedicated Power switch on the OnOff cluster
# if the mains power is off - treat it as if the HVAC mode is off
self._attr_hvac_mode = HVACMode.OFF
self._attr_hvac_action = None
return

# update hvac_mode from SystemMode
system_mode_value = int(
self.get_matter_attribute_value(clusters.Thermostat.Attributes.SystemMode)
Expand Down
16 changes: 15 additions & 1 deletion homeassistant/components/matter/fan.py
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,14 @@ def _update_from_device(self) -> None:
"""Update from device."""
if not hasattr(self, "_attr_preset_modes"):
self._calculate_features()

if self.get_matter_attribute_value(clusters.OnOff.Attributes.OnOff) is False:
# special case: the appliance has a dedicated Power switch on the OnOff cluster
# if the mains power is off - treat it as if the fan mode is off
self._attr_preset_mode = None
self._attr_percentage = 0
return

if self._attr_supported_features & FanEntityFeature.DIRECTION:
direction_value = self.get_matter_attribute_value(
clusters.FanControl.Attributes.AirflowDirection
Expand Down Expand Up @@ -200,7 +208,13 @@ def _update_from_device(self) -> None:
wind_setting = self.get_matter_attribute_value(
clusters.FanControl.Attributes.WindSetting
)
if (
fan_mode = self.get_matter_attribute_value(
clusters.FanControl.Attributes.FanMode
)
if fan_mode == clusters.FanControl.Enums.FanModeEnum.kOff:
self._attr_preset_mode = None
self._attr_percentage = 0
elif (
self._attr_preset_modes
and PRESET_NATURAL_WIND in self._attr_preset_modes
and wind_setting & WindBitmap.kNaturalWind
Expand Down
9 changes: 7 additions & 2 deletions tests/components/matter/test_climate.py
Original file line number Diff line number Diff line change
Expand Up @@ -315,14 +315,19 @@ async def test_room_airconditioner(
state = hass.states.get("climate.room_airconditioner_thermostat")
assert state
assert state.attributes["current_temperature"] == 20
assert state.attributes["min_temp"] == 16
assert state.attributes["max_temp"] == 32
# room airconditioner has mains power on OnOff cluster with value set to False
assert state.state == HVACMode.OFF

# test supported features correctly parsed
# WITHOUT temperature_range support
mask = ClimateEntityFeature.TARGET_TEMPERATURE | ClimateEntityFeature.TURN_OFF
assert state.attributes["supported_features"] & mask == mask

# set mains power to ON (OnOff cluster)
set_node_attribute(room_airconditioner, 1, 6, 0, True)
await trigger_subscription_callback(hass, matter_client)
state = hass.states.get("climate.room_airconditioner_thermostat")

# test supported HVAC modes include fan and dry modes
assert state.attributes["hvac_modes"] == [
HVACMode.OFF,
Expand Down
6 changes: 6 additions & 0 deletions tests/components/matter/test_fan.py
Original file line number Diff line number Diff line change
Expand Up @@ -92,6 +92,12 @@ async def test_fan_base(
await trigger_subscription_callback(hass, matter_client)
state = hass.states.get(entity_id)
assert state.attributes["preset_mode"] == "sleep_wind"
# set mains power to OFF (OnOff cluster)
set_node_attribute(air_purifier, 1, 6, 0, False)
await trigger_subscription_callback(hass, matter_client)
state = hass.states.get(entity_id)
assert state.attributes["preset_mode"] is None
assert state.attributes["percentage"] == 0


async def test_fan_turn_on_with_percentage(
Expand Down

0 comments on commit 1fa6972

Please sign in to comment.