8000 Add turnonbehaviormodule for iot by rytilahti · Pull Request #1288 · python-kasa/python-kasa · GitHub
[go: up one dir, main page]

Skip to content

Add turnonbehaviormodule for iot #1288

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 1 commit into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
64 changes: 7 additions & 57 deletions kasa/iot/iotbulb.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,7 @@

import logging
import re
from dataclasses import dataclass
from enum import Enum
from typing import Annotated, cast

from mashumaro import DataClassDictMixin
from mashumaro.config import BaseConfig
from mashumaro.types import Alias
from typing import cast

from ..device_type import DeviceType
from ..deviceconfig import DeviceConfig
Expand All @@ -27,58 +21,10 @@
LightPreset,
Schedule,
Time,
TurnOnBehaviorModule,
Usage,
)


class BehaviorMode(str, Enum):
"""Enum to present type of turn on behavior."""

#: Return to the last state known state.
Last = "last_status"
#: Use chosen preset.
Preset = "customize_preset"
#: Circadian
Circadian = "circadian"


@dataclass
class TurnOnBehavior(DataClassDictMixin):
"""Model to present a single turn on behavior.

:param int preset: the index number of wanted preset.
:param BehaviorMode mode: last status or preset mode.
If you are changing existing settings, you should not set this manually.

To change the behavior, it is only necessary to change the :attr:`preset` field
to contain either the preset index, or ``None`` for the last known state.
"""

class Config(BaseConfig):
"""Serialization config."""

omit_none = True
serialize_by_alias = True

#: Wanted behavior
mode: BehaviorMode
#: Index of preset to use, or ``None`` for the last known state.
preset: Annotated[int | None, Alias("index")] = None
brightness: int | None = None
color_temp: int | None = None
hue: int | None = None
saturation: int | None = None


@dataclass
class TurnOnBehaviors(DataClassDictMixin):
"""Model to contain turn on behaviors."""

#: The behavior when the bulb is turned on programmatically.
soft: Annotated[TurnOnBehavior, Alias("soft_on")]
#: The behavior when the bulb has been off from mains power.
hard: Annotated[TurnOnBehavior, Alias("hard_on")]

from .modules.turnonbehavior import TurnOnBehaviors

TPLINK_KELVIN = {
"LB130": ColorTempRange(2500, 9000),
Expand Down Expand Up @@ -222,6 +168,10 @@ async def _initialize_modules(self) -> None:
Module.IotAntitheft, Antitheft(self, "smartlife.iot.common.anti_theft")
)
self.add_module(Module.Time, Time(self, "smartlife.iot.common.timesetting"))
self.add_module(
Module.IotTurnOnBehavior,
TurnOnBehaviorModule(self, "smartlife.iot.smartbulb.lightingservice"),
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Named as Module, as TurnOnBehavior is already taken by the model... We probably want to make a breaking change here, and rename the models to something else.

)
self.add_module(Module.Energy, Emeter(self, self.emeter_type))
self.add_module(Module.IotCountdown, Countdown(self, "countdown"))
self.add_module(Module.IotCloud, Cloud(self, "smartlife.iot.common.cloud"))
Expand Down
2 changes: 2 additions & 0 deletions kasa/iot/modules/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
from .rulemodule import Rule, RuleModule
from .schedule import Schedule
from .time import Time
from .turnonbehavior import TurnOnBehaviorModule
from .usage import Usage

__all__ = [
Expand All @@ -31,5 +32,6 @@
"RuleModule",
"Schedule",
"Time",
"TurnOnBehaviorModule",
"Usage",
]
125 changes: 125 additions & 0 deletions kasa/iot/modules/turnonbehavior.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
"""Implementation of the turn on behavior for bulbs."""

from __future__ import annotations

import logging
from dataclasses import dataclass
from enum import Enum
from typing import Annotated

from mashumaro import DataClassDictMixin
from mashumaro.config import BaseConfig
from mashumaro.types import Alias

from ...feature import Feature
from ..iotmodule import IotModule

_LOGGER = logging.getLogger(__name__)


class TurnOnBehaviorModule(IotModule):
"""Implements the turn on behavior module."""

def query(self) -> dict:
"""Request default behavior configuration."""
return self.query_for_command("get_default_behavior")

def _initialize_features(self) -> None:
"""Initialize features after the initial update."""
# Only add features if the device supports the module
if "get_default_behavior" not in self.data:
return

self._add_feature(
Feature(
device=self._device,
container=self,
id="turn_on_hard",
name="Turn on hard",
icon="mdi:motion-sensor",
attribute_getter="turn_on_hard",
# attribute_setter="set_turn_on_hard",
type=Feature.Type.Choice,
choices_getter=lambda: list(BehaviorMode),
category=Feature.Category.Config,
)
)

self._add_feature(
Feature(
device=self._device,
container=self,
id="turn_on_soft",
name="Turn on soft",
icon="mdi:motion-sensor",
attribute_getter="turn_on_soft",
# attribute_setter="set_turn_on_hard",
type=Feature.Type.Choice,
choices_getter=lambda: list(BehaviorMode),
category=Feature.Category.Config,
)
)

@property
def behaviors(self) -> TurnOnBehaviors:
"""Current turn on behaviors."""
return TurnOnBehaviors.from_dict(self.data["get_default_behavior"])

@property
def turn_on_hard(self) -> BehaviorMode:
"""Current turn on hard behavior."""
return self.behaviors.hard.mode

@property
def turn_on_soft(self) -> BehaviorMode:
"""Current turn on soft behavior."""
return self.behaviors.hard.mode


class BehaviorMode(str, Enum):
"""Enum to present type of turn on behavior."""

#: Return to the last state known state.
Last = "last_status"
#: Use chosen preset.
Preset = "customize_preset"
#: Circadian
Circadian = "circadian"


@dataclass
class TurnOnBehavior(DataClassDictMixin):
"""Model to present a single turn on behavior.

:param int preset: the index number of wanted preset.
:param BehaviorMode mode: last status or preset mode.
If you are changing existing settings, you should not set this manually.

To change the behavior, it is only necessary to change the :attr:`preset` field
to contain either the preset index, or ``None`` for the last known state.
"""

class Config(BaseConfig):
"""Serialization config."""

omit_none = True
serialize_by_alias = True

#: Wanted behavior
mode: BehaviorMode
#: Index of preset to use, or ``None`` for the last known state.
preset: Annotated[int | None, Alias("index")] = None
brightness: int | None = None
color_temp: int | None = None
hue: int | None = None
saturation: int | None = None


@dataclass
class TurnOnBehaviors(DataClassDictMixin):
"""Model to contain turn on behaviors."""

#: The behavior when the bulb is turned on programmatically.
soft: Annotated[TurnOnBehavior, Alias("soft_on")]
#: The behavior when the bulb has been off from mains power.
hard: Annotated[TurnOnBehavior, Alias("hard_on")]
3 changes: 3 additions & 0 deletions kasa/module.py
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,9 @@ class Module(ABC):
IotSchedule: Final[ModuleName[iot.Schedule]] = ModuleName("schedule")
IotUsage: Final[ModuleName[iot.Usage]] = ModuleName("usage")
IotCloud: Final[ModuleName[iot.Cloud]] = ModuleName("cloud")
IotTurnOnBehavior: Final[ModuleName[iot.TurnOnBehaviorModule]] = ModuleName(
"turnonbehavior"
)

# SMART only Modules
Alarm: Final[ModuleName[smart.Alarm]] = ModuleName("Alarm")
Expand Down
Loading
0