mirror of
https://github.com/home-assistant/core.git
synced 2026-09-08 22:51:33 +01:00
139 lines
4.3 KiB
Python
139 lines
4.3 KiB
Python
"""Component providing support for Reolink time entities."""
|
|
|
|
from collections.abc import Callable
|
|
from dataclasses import dataclass
|
|
from datetime import time
|
|
from typing import Any, override
|
|
|
|
from reolink_aio.api import Host
|
|
from reolink_aio.enums import SpotlightModeEnum
|
|
|
|
from homeassistant.components.time import TimeEntity, TimeEntityDescription
|
|
from homeassistant.const import EntityCategory
|
|
from homeassistant.core import HomeAssistant
|
|
from homeassistant.helpers.entity_platform import AddConfigEntryEntitiesCallback
|
|
|
|
from .entity import ReolinkChannelCoordinatorEntity, ReolinkChannelEntityDescription
|
|
from .util import ReolinkConfigEntry, ReolinkData, raise_translated_error
|
|
|
|
PARALLEL_UPDATES = 0
|
|
|
|
|
|
@dataclass(frozen=True, kw_only=True)
|
|
class ReolinkTimeEntityDescription(
|
|
TimeEntityDescription,
|
|
ReolinkChannelEntityDescription,
|
|
):
|
|
"""A class that describes time entities."""
|
|
|
|
method: Callable[[Host, int, time], Any]
|
|
value: Callable[[Host, int], time | None]
|
|
|
|
|
|
def _schedule_time(api: Host, ch: int, prefix: str) -> time | None:
|
|
"""Return the start or end time of the floodlight schedule."""
|
|
schedule = api.whiteled_schedule(ch)
|
|
if not schedule:
|
|
return None
|
|
return time(hour=schedule[f"{prefix}Hour"], minute=schedule[f"{prefix}Min"])
|
|
|
|
|
|
def _set_start(api: Host, ch: int, value: time) -> Any:
|
|
"""Set the start time of the floodlight schedule."""
|
|
schedule = api.whiteled_schedule(ch) or {}
|
|
return api.set_spotlight_lighting_schedule(
|
|
ch,
|
|
schedule.get("EndHour", 0),
|
|
schedule.get("EndMin", 0),
|
|
value.hour,
|
|
value.minute,
|
|
)
|
|
|
|
|
|
def _set_end(api: Host, ch: int, value: time) -> Any:
|
|
"""Set the end time of the floodlight schedule."""
|
|
schedule = api.whiteled_schedule(ch) or {}
|
|
return api.set_spotlight_lighting_schedule(
|
|
ch,
|
|
value.hour,
|
|
value.minute,
|
|
schedule.get("StartHour", 0),
|
|
schedule.get("StartMin", 0),
|
|
)
|
|
|
|
|
|
TIME_ENTITIES = (
|
|
ReolinkTimeEntityDescription(
|
|
key="floodlight_schedule_start",
|
|
cmd_key="GetWhiteLed",
|
|
cmd_id=[289, 438],
|
|
translation_key="floodlight_schedule_start",
|
|
entity_category=EntityCategory.CONFIG,
|
|
entity_registry_enabled_default=False,
|
|
supported=lambda api, ch: (
|
|
SpotlightModeEnum.schedule.name in api.whiteled_mode_list(ch)
|
|
),
|
|
value=lambda api, ch: _schedule_time(api, ch, "Start"),
|
|
method=_set_start,
|
|
),
|
|
ReolinkTimeEntityDescription(
|
|
key="floodlight_schedule_end",
|
|
cmd_key="GetWhiteLed",
|
|
cmd_id=[289, 438],
|
|
translation_key="floodlight_schedule_end",
|
|
entity_category=EntityCategory.CONFIG,
|
|
entity_registry_enabled_default=False,
|
|
supported=lambda api, ch: (
|
|
SpotlightModeEnum.schedule.name in api.whiteled_mode_list(ch)
|
|
),
|
|
value=lambda api, ch: _schedule_time(api, ch, "End"),
|
|
method=_set_end,
|
|
),
|
|
)
|
|
|
|
|
|
async def async_setup_entry(
|
|
hass: HomeAssistant,
|
|
config_entry: ReolinkConfigEntry,
|
|
async_add_entities: AddConfigEntryEntitiesCallback,
|
|
) -> None:
|
|
"""Set up Reolink time entities."""
|
|
reolink_data = config_entry.runtime_data
|
|
api = reolink_data.host.api
|
|
|
|
async_add_entities(
|
|
ReolinkTimeEntity(reolink_data, channel, entity_description)
|
|
for entity_description in TIME_ENTITIES
|
|
for channel in api.channels
|
|
if entity_description.supported(api, channel)
|
|
)
|
|
|
|
|
|
class ReolinkTimeEntity(ReolinkChannelCoordinatorEntity, TimeEntity):
|
|
"""Base time entity class for Reolink IP cameras."""
|
|
|
|
entity_description: ReolinkTimeEntityDescription
|
|
|
|
def __init__(
|
|
self,
|
|
reolink_data: ReolinkData,
|
|
channel: int,
|
|
entity_description: ReolinkTimeEntityDescription,
|
|
) -> None:
|
|
"""Initialize Reolink time entity."""
|
|
self.entity_description = entity_description
|
|
super().__init__(reolink_data, channel)
|
|
|
|
@property
|
|
@override
|
|
def native_value(self) -> time | None:
|
|
"""Return the current value."""
|
|
return self.entity_description.value(self._host.api, self._channel)
|
|
|
|
@raise_translated_error
|
|
@override
|
|
async def async_set_value(self, value: time) -> None:
|
|
"""Update the current value."""
|
|
await self.entity_description.method(self._host.api, self._channel, value)
|
|
self.async_write_ha_state()
|