Skip to content

Commit

Permalink
Add height sensor to Idasen Desk integration (#103324)
Browse files Browse the repository at this point in the history
  • Loading branch information
abmantis committed Nov 20, 2023
1 parent 7160e95 commit e6226b0
Show file tree
Hide file tree
Showing 8 changed files with 139 additions and 4 deletions.
2 changes: 1 addition & 1 deletion homeassistant/components/idasen_desk/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@

from .const import DOMAIN

PLATFORMS: list[Platform] = [Platform.BUTTON, Platform.COVER]
PLATFORMS: list[Platform] = [Platform.BUTTON, Platform.COVER, Platform.SENSOR]

_LOGGER = logging.getLogger(__name__)

Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/idasen_desk/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -12,5 +12,5 @@
"documentation": "https://www.home-assistant.io/integrations/idasen_desk",
"iot_class": "local_push",
"quality_scale": "silver",
"requirements": ["idasen-ha==2.3"]
"requirements": ["idasen-ha==2.4"]
}
100 changes: 100 additions & 0 deletions homeassistant/components/idasen_desk/sensor.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
"""Representation of Idasen Desk sensors."""
from __future__ import annotations

from collections.abc import Callable
from dataclasses import dataclass
from typing import Any

from homeassistant import config_entries
from homeassistant.components.sensor import (
SensorDeviceClass,
SensorEntity,
SensorEntityDescription,
SensorStateClass,
)
from homeassistant.const import UnitOfLength
from homeassistant.core import HomeAssistant, callback
from homeassistant.helpers.device_registry import DeviceInfo
from homeassistant.helpers.entity_platform import AddEntitiesCallback
from homeassistant.helpers.update_coordinator import CoordinatorEntity

from . import DeskData, IdasenDeskCoordinator
from .const import DOMAIN


@dataclass
class IdasenDeskSensorDescriptionMixin:
"""Required values for IdasenDesk sensors."""

value_fn: Callable[[IdasenDeskCoordinator], float | None]


@dataclass
class IdasenDeskSensorDescription(
SensorEntityDescription,
IdasenDeskSensorDescriptionMixin,
):
"""Class describing IdasenDesk sensor entities."""


SENSORS = (
IdasenDeskSensorDescription(
key="height",
translation_key="height",
icon="mdi:arrow-up-down",
native_unit_of_measurement=UnitOfLength.METERS,
device_class=SensorDeviceClass.DISTANCE,
state_class=SensorStateClass.MEASUREMENT,
entity_registry_enabled_default=False,
suggested_display_precision=3,
value_fn=lambda coordinator: coordinator.desk.height,
),
)


async def async_setup_entry(
hass: HomeAssistant,
entry: config_entries.ConfigEntry,
async_add_entities: AddEntitiesCallback,
) -> None:
"""Set up Idasen Desk sensors."""
data: DeskData = hass.data[DOMAIN][entry.entry_id]
async_add_entities(
IdasenDeskSensor(
data.address, data.device_info, data.coordinator, sensor_description
)
for sensor_description in SENSORS
)


class IdasenDeskSensor(CoordinatorEntity, SensorEntity):
"""IdasenDesk sensor."""

entity_description: IdasenDeskSensorDescription
_attr_has_entity_name = True

def __init__(
self,
address: str,
device_info: DeviceInfo,
coordinator: IdasenDeskCoordinator,
description: IdasenDeskSensorDescription,
) -> None:
"""Initialize the IdasenDesk sensor entity."""
super().__init__(coordinator)
self.entity_description = description

self._attr_unique_id = f"{description.key}-{address}"
self._attr_device_info = device_info
self._address = address

async def async_added_to_hass(self) -> None:
"""When entity is added to hass."""
await super().async_added_to_hass()
self._handle_coordinator_update()

@callback
def _handle_coordinator_update(self, *args: Any) -> None:
"""Handle data update."""
self._attr_native_value = self.entity_description.value_fn(self.coordinator)
super()._handle_coordinator_update()
7 changes: 7 additions & 0 deletions homeassistant/components/idasen_desk/strings.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,5 +19,12 @@
"already_configured": "[%key:common::config_flow::abort::already_configured_device%]",
"no_devices_found": "No unconfigured devices found. Make sure that the desk is in Bluetooth pairing mode. Enter pairing mode by pressing the small button with the Bluetooth logo on the controller for about 3 seconds, until it starts blinking."
}
},
"entity": {
"sensor": {
"height": {
"name": "Height"
}
}
}
}
2 changes: 1 addition & 1 deletion requirements_all.txt
Original file line number Diff line number Diff line change
Expand Up @@ -1061,7 +1061,7 @@ ical==6.1.0
icmplib==3.0

# homeassistant.components.idasen_desk
idasen-ha==2.3
idasen-ha==2.4

# homeassistant.components.network
ifaddr==0.2.0
Expand Down
2 changes: 1 addition & 1 deletion requirements_test_all.txt
Original file line number Diff line number Diff line change
Expand Up @@ -836,7 +836,7 @@ ical==6.1.0
icmplib==3.0

# homeassistant.components.idasen_desk
idasen-ha==2.3
idasen-ha==2.4

# homeassistant.components.network
ifaddr==0.2.0
Expand Down
1 change: 1 addition & 0 deletions tests/components/idasen_desk/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@ async def mock_move_down():
mock_desk.move_up = AsyncMock(side_effect=mock_move_up)
mock_desk.move_down = AsyncMock(side_effect=mock_move_down)
mock_desk.stop = AsyncMock()
mock_desk.height = 1
mock_desk.height_percent = 60
mock_desk.is_moving = False
mock_desk.address = "AA:BB:CC:DD:EE:FF"
Expand Down
27 changes: 27 additions & 0 deletions tests/components/idasen_desk/test_sensors.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
"""Test the IKEA Idasen Desk sensors."""
from unittest.mock import MagicMock

from homeassistant.core import HomeAssistant

from . import init_integration


async def test_height_sensor(
hass: HomeAssistant,
mock_desk_api: MagicMock,
entity_registry_enabled_by_default: None,
) -> None:
"""Test height sensor."""
await init_integration(hass)

entity_id = "sensor.test_height"
state = hass.states.get(entity_id)
assert state
assert state.state == "1"

mock_desk_api.height = 1.2
mock_desk_api.trigger_update_callback(None)

state = hass.states.get(entity_id)
assert state
assert state.state == "1.2"

0 comments on commit e6226b0

Please sign in to comment.