async def test_attributes(caplog, aio_httpclient): caplog.set_level(logging.DEBUG) auth = MagicMock() aio_httpclient.get.return_value = MockResponse(json.dumps(DATA1), 200) aircon = Aircon(BackendSelectorMock(), auth, SAID, None) await aircon.connect() assert aircon.get_online() is False assert aircon.get_power_on() is False assert aircon.get_display_on() is False assert aircon.get_current_temp() == 23 assert aircon.get_current_humidity() == 56 assert aircon.get_temp() == 30 assert aircon.get_humidity() == 40 assert aircon.get_mode() == Mode.Heat assert aircon.get_sixthsense_mode() is False assert aircon.get_fanspeed() == FanSpeed.Off assert aircon.get_h_louver_swing() is True assert aircon.get_turbo_mode() is False assert aircon.get_eco_mode() is False assert aircon.get_quiet_mode() is False await aircon.disconnect() aio_httpclient.get.return_value = MockResponse(json.dumps(DATA2), 200) await aircon.connect() assert aircon.get_online() is True assert aircon.get_power_on() is True assert aircon.get_display_on() is True assert aircon.get_current_temp() == 30 assert aircon.get_current_humidity() == 31 assert aircon.get_temp() == 29 assert aircon.get_humidity() == 45 assert aircon.get_mode() == Mode.Fan assert aircon.get_sixthsense_mode() is True assert aircon.get_fanspeed() == FanSpeed.Auto assert aircon.get_h_louver_swing() is False assert aircon.get_turbo_mode() is True assert aircon.get_eco_mode() is True assert aircon.get_quiet_mode() is True await aircon.disconnect()
def print_status(ac: Aircon): print("online: " + str(ac.get_online())) print("power_on: " + str(ac.get_power_on())) print("temp: " + str(ac.get_temp())) print("humidity: " + str(ac.get_humidity())) print("current_temp: " + str(ac.get_current_temp())) print("current_humidity: " + str(ac.get_current_humidity())) print("mode: " + str(ac.get_mode())) print("sixthsense_mode: " + str(ac.get_sixthsense_mode())) print("fanspeed: " + str(ac.get_fanspeed())) print("h_louver_swing: " + str(ac.get_h_louver_swing())) print("turbo_mode: " + str(ac.get_turbo_mode())) print("eco_mode: " + str(ac.get_eco_mode())) print("quiet_mode: " + str(ac.get_quiet_mode())) print("display_on: " + str(ac.get_display_on()))
class AirConEntity(ClimateEntity): """Representation of an air conditioner.""" _attr_fan_modes = SUPPORTED_FAN_MODES _attr_hvac_modes = SUPPORTED_HVAC_MODES _attr_max_temp = SUPPORTED_MAX_TEMP _attr_min_temp = SUPPORTED_MIN_TEMP _attr_supported_features = ( ClimateEntityFeature.TARGET_TEMPERATURE | ClimateEntityFeature.FAN_MODE | ClimateEntityFeature.SWING_MODE ) _attr_swing_modes = SUPPORTED_SWING_MODES _attr_target_temperature_step = SUPPORTED_TARGET_TEMPERATURE_STEP _attr_temperature_unit = TEMP_CELSIUS _attr_should_poll = False def __init__(self, hass, said, name, backend_selector: BackendSelector, auth: Auth): """Initialize the entity.""" self._aircon = Aircon(backend_selector, auth, said, self.async_write_ha_state) self.entity_id = generate_entity_id(ENTITY_ID_FORMAT, said, hass=hass) self._attr_name = name if name is not None else said self._attr_unique_id = said async def async_added_to_hass(self) -> None: """Connect aircon to the cloud.""" await self._aircon.connect() @property def available(self) -> bool: """Return True if entity is available.""" return self._aircon.get_online() @property def current_temperature(self) -> float: """Return the current temperature.""" return self._aircon.get_current_temp() @property def target_temperature(self) -> float: """Return the temperature we try to reach.""" return self._aircon.get_temp() async def async_set_temperature(self, **kwargs: Any) -> None: """Set new target temperature.""" await self._aircon.set_temp(kwargs.get(ATTR_TEMPERATURE)) @property def current_humidity(self) -> int: """Return the current humidity.""" return self._aircon.get_current_humidity() @property def target_humidity(self) -> int: """Return the humidity we try to reach.""" return self._aircon.get_humidity() async def async_set_humidity(self, humidity: int) -> None: """Set new target humidity.""" await self._aircon.set_humidity(humidity) @property def hvac_mode(self) -> HVACMode | None: """Return current operation ie. heat, cool, fan.""" if not self._aircon.get_power_on(): return HVACMode.OFF mode: AirconMode = self._aircon.get_mode() return AIRCON_MODE_MAP.get(mode) async def async_set_hvac_mode(self, hvac_mode: HVACMode) -> None: """Set HVAC mode.""" if hvac_mode == HVACMode.OFF: await self._aircon.set_power_on(False) return if not (mode := HVAC_MODE_TO_AIRCON_MODE.get(hvac_mode)): raise ValueError(f"Invalid hvac mode {hvac_mode}") await self._aircon.set_mode(mode) if not self._aircon.get_power_on(): await self._aircon.set_power_on(True)
class AirConEntity(ClimateEntity): """Representation of an air conditioner.""" _attr_fan_modes = SUPPORTED_FAN_MODES _attr_hvac_modes = SUPPORTED_HVAC_MODES _attr_max_temp = SUPPORTED_MAX_TEMP _attr_min_temp = SUPPORTED_MIN_TEMP _attr_supported_features = (ClimateEntityFeature.TARGET_TEMPERATURE | ClimateEntityFeature.FAN_MODE | ClimateEntityFeature.SWING_MODE) _attr_swing_modes = SUPPORTED_SWING_MODES _attr_target_temperature_step = SUPPORTED_TARGET_TEMPERATURE_STEP _attr_temperature_unit = TEMP_CELSIUS _attr_should_poll = False def __init__(self, said, auth: Auth): """Initialize the entity.""" self._aircon = Aircon(auth, said, self.async_write_ha_state) self._attr_name = said self._attr_unique_id = said async def async_added_to_hass(self) -> None: """Connect aircon to the cloud.""" await self._aircon.connect() try: name = await self._aircon.fetch_name() if name is not None: self._attr_name = name except (asyncio.TimeoutError, aiohttp.ClientError): _LOGGER.exception("Failed to get name") @property def available(self) -> bool: """Return True if entity is available.""" return self._aircon.get_online() @property def current_temperature(self): """Return the current temperature.""" return self._aircon.get_current_temp() @property def target_temperature(self): """Return the temperature we try to reach.""" return self._aircon.get_temp() async def async_set_temperature(self, **kwargs): """Set new target temperature.""" await self._aircon.set_temp(kwargs.get(ATTR_TEMPERATURE)) @property def current_humidity(self): """Return the current humidity.""" return self._aircon.get_current_humidity() @property def target_humidity(self): """Return the humidity we try to reach.""" return self._aircon.get_humidity() async def async_set_humidity(self, humidity: int) -> None: """Set new target humidity.""" await self._aircon.set_humidity(humidity) @property def hvac_mode(self): """Return current operation ie. heat, cool, fan.""" if not self._aircon.get_power_on(): return HVAC_MODE_OFF mode: AirconMode = self._aircon.get_mode() return AIRCON_MODE_MAP.get(mode) async def async_set_hvac_mode(self, hvac_mode): """Set HVAC mode.""" if hvac_mode == HVAC_MODE_OFF: await self._aircon.set_power_on(False) return if not (mode := HVAC_MODE_TO_AIRCON_MODE.get(hvac_mode)): raise ValueError(f"Invalid hvac mode {hvac_mode}") await self._aircon.set_mode(mode) if not self._aircon.get_power_on(): await self._aircon.set_power_on(True)
class AirConEntity(ClimateEntity): """Representation of an air conditioner.""" def __init__(self, said, auth: Auth): """Initialize the entity.""" self._aircon = Aircon(auth, said, self.schedule_update_ha_state) self._supported_features = SUPPORT_TARGET_TEMPERATURE self._supported_features |= SUPPORT_FAN_MODE self._supported_features |= SUPPORT_SWING_MODE async def _async_connect(self): """Connect aircon to the cloud.""" await self._aircon.connect() @property def min_temp(self) -> float: """Return the minimum temperature.""" return 16 @property def max_temp(self) -> float: """Return the maximum temperature.""" return 30 @property def supported_features(self): """Return the list of supported features.""" return self._supported_features @property def name(self): """Return the name of the aircon.""" return self._aircon._said # TODO: return user-given-name from the API @property def unique_id(self): """Return a unique ID.""" return self._aircon._said @property def available(self) -> bool: """Return True if entity is available.""" return self._aircon.get_online() @property def temperature_unit(self): """Return the unit of measurement which this thermostat uses.""" return TEMP_CELSIUS @property def current_temperature(self): """Return the current temperature.""" return self._aircon.get_current_temp() @property def target_temperature(self): """Return the temperature we try to reach.""" return self._aircon.get_temp() @property def target_temperature_step(self): """Return the supported step of target temperature.""" return 1 async def async_set_temperature(self, **kwargs): """Set new target temperature.""" await self._aircon.set_temp(kwargs.get(ATTR_TEMPERATURE)) @property def current_humidity(self): """Return the current humidity.""" return self._aircon.get_current_humidity() @property def target_humidity(self): """Return the humidity we try to reach.""" return self._aircon.get_humidity() @property def target_humidity_step(self): """Return the supported step of target humidity.""" return 10 async def async_set_humidity(self, **kwargs): """Set new target humidity.""" await self._aircon.set_humidity(kwargs.get(ATTR_HUMIDITY)) @property def hvac_modes(self): """Return the list of available operation modes.""" return [ HVAC_MODE_COOL, HVAC_MODE_HEAT, HVAC_MODE_FAN_ONLY, HVAC_MODE_OFF ] @property def hvac_mode(self): """Return current operation ie. heat, cool, fan.""" if not self._aircon.get_power_on(): return HVAC_MODE_OFF mode: AirconMode = self._aircon.get_mode() if mode == AirconMode.Cool: return HVAC_MODE_COOL elif mode == AirconMode.Heat: return HVAC_MODE_HEAT elif mode == AirconMode.Fan: return HVAC_MODE_FAN_ONLY return None async def async_set_hvac_mode(self, hvac_mode): """Set HVAC mode.""" if hvac_mode == HVAC_MODE_OFF: await self._aircon.set_power_on(False) mode = None if hvac_mode == HVAC_MODE_COOL: mode = AirconMode.Cool elif hvac_mode == HVAC_MODE_HEAT: mode = AirconMode.Heat elif hvac_mode == HVAC_MODE_FAN_ONLY: mode = AirconMode.Fan if not mode: return await self._aircon.set_mode(mode) if not self._aircon.get_power_on(): await self._aircon.set_power_on(True) @property def fan_modes(self): """List of available fan modes.""" return [FAN_OFF, FAN_AUTO, FAN_LOW, FAN_MEDIUM, FAN_HIGH] @property def fan_mode(self): """Return the fan setting.""" fanspeed = self._aircon.get_fanspeed() if fanspeed == AirconFanSpeed.Auto: return FAN_AUTO elif fanspeed == AirconFanSpeed.Low: return FAN_LOW elif fanspeed == AirconFanSpeed.Medium: return FAN_MEDIUM elif fanspeed == AirconFanSpeed.High: return FAN_HIGH return FAN_OFF async def async_set_fan_mode(self, fan_mode): """Set fan mode.""" fanspeed = None if fan_mode == FAN_AUTO: fanspeed = AirconFanSpeed.Auto elif fan_mode == FAN_LOW: fanspeed = AirconFanSpeed.Low elif fan_mode == FAN_MEDIUM: fanspeed = AirconFanSpeed.Medium elif fan_mode == FAN_HIGH: fanspeed = AirconFanSpeed.High if not fanspeed: return await self._aircon.set_fanspeed(fanspeed) @property def swing_modes(self): """List of available swing modes.""" return [SWING_HORIZONTAL, SWING_OFF] @property def swing_mode(self): """Return the swing setting.""" return SWING_HORIZONTAL if self._aircon.get_h_louver_swing( ) else SWING_OFF async def async_set_swing_mode(self, swing_mode): """Set new target temperature.""" if swing_mode == SWING_HORIZONTAL: await self._aircon.set_h_louver_swing(True) else: await self._aircon.set_h_louver_swing(False) async def async_turn_on(self): """Turn device on.""" await self._aircon.set_power_on(True) async def async_turn_off(self): """Turn device off.""" await self._aircon.set_power_on(False)
class AirConEntity(ClimateEntity): """Representation of an air conditioner.""" _attr_fan_modes = [FAN_AUTO, FAN_HIGH, FAN_MEDIUM, FAN_LOW, FAN_OFF] _attr_hvac_modes = [ HVAC_MODE_COOL, HVAC_MODE_HEAT, HVAC_MODE_FAN_ONLY, HVAC_MODE_OFF, ] _attr_max_temp = 30 _attr_min_temp = 16 _attr_supported_features = (SUPPORT_TARGET_TEMPERATURE | SUPPORT_FAN_MODE | SUPPORT_SWING_MODE) _attr_swing_modes = [SWING_HORIZONTAL, SWING_OFF] _attr_target_temperature_step = 1 _attr_temperature_unit = TEMP_CELSIUS _attr_should_poll = False def __init__(self, said, auth: Auth): """Initialize the entity.""" self._aircon = Aircon(auth, said, self.async_write_ha_state) self._attr_name = said self._attr_unique_id = said async def async_added_to_hass(self) -> None: """Connect aircon to the cloud.""" await self._aircon.connect() try: name = await self._aircon.fetch_name() if name is not None: self._attr_name = name except (asyncio.TimeoutError, aiohttp.ClientError): _LOGGER.exception("Failed to get name") @property def available(self) -> bool: """Return True if entity is available.""" return self._aircon.get_online() @property def current_temperature(self): """Return the current temperature.""" return self._aircon.get_current_temp() @property def target_temperature(self): """Return the temperature we try to reach.""" return self._aircon.get_temp() async def async_set_temperature(self, **kwargs): """Set new target temperature.""" await self._aircon.set_temp(kwargs.get(ATTR_TEMPERATURE)) @property def current_humidity(self): """Return the current humidity.""" return self._aircon.get_current_humidity() @property def target_humidity(self): """Return the humidity we try to reach.""" return self._aircon.get_humidity() async def async_set_humidity(self, humidity: int) -> None: """Set new target humidity.""" await self._aircon.set_humidity(humidity) @property def hvac_mode(self): """Return current operation ie. heat, cool, fan.""" if not self._aircon.get_power_on(): return HVAC_MODE_OFF mode: AirconMode = self._aircon.get_mode() return AIRCON_MODE_MAP.get(mode, None) async def async_set_hvac_mode(self, hvac_mode): """Set HVAC mode.""" if hvac_mode == HVAC_MODE_OFF: await self._aircon.set_power_on(False) return mode = HVAC_MODE_TO_AIRCON_MODE.get(hvac_mode) if not mode: _LOGGER.warning("Unexpected hvac mode: %s", hvac_mode) return await self._aircon.set_mode(mode) if not self._aircon.get_power_on(): await self._aircon.set_power_on(True) @property def fan_mode(self): """Return the fan setting.""" fanspeed = self._aircon.get_fanspeed() return AIRCON_FANSPEED_MAP.get(fanspeed, FAN_OFF) async def async_set_fan_mode(self, fan_mode): """Set fan mode.""" fanspeed = FAN_MODE_TO_AIRCON_FANSPEED.get(fan_mode) if not fanspeed: return await self._aircon.set_fanspeed(fanspeed) @property def swing_mode(self): """Return the swing setting.""" return SWING_HORIZONTAL if self._aircon.get_h_louver_swing( ) else SWING_OFF async def async_set_swing_mode(self, swing_mode): """Set new target temperature.""" await self._aircon.set_h_louver_swing(swing_mode == SWING_HORIZONTAL) async def async_turn_on(self): """Turn device on.""" await self._aircon.set_power_on(True) async def async_turn_off(self): """Turn device off.""" await self._aircon.set_power_on(False)