This commit is contained in:
Victor Alexandrovich Tsyrenschikov
2026-03-30 20:25:42 +05:00
parent 139f9f1bd2
commit 373ed28445
2449 changed files with 53602 additions and 0 deletions

View File

@@ -0,0 +1,195 @@
"""Schema for event property.
https://yandex.ru/dev/dialogs/smart-home/doc/concepts/event.html
"""
from __future__ import annotations
from enum import StrEnum
from typing import Any, Generic, Literal, TypeVar
from pydantic import BaseModel, ConfigDict, field_validator
from .base import APIModel
class EventPropertyInstance(StrEnum):
"""Instance of an event property.
https://yandex.ru/dev/dialogs/smart-home/doc/concepts/event-instance.html
"""
VIBRATION = "vibration"
OPEN = "open"
BUTTON = "button"
MOTION = "motion"
SMOKE = "smoke"
GAS = "gas"
BATTERY_LEVEL = "battery_level"
FOOD_LEVEL = "food_level"
WATER_LEVEL = "water_level"
WATER_LEAK = "water_leak"
class EventInstanceEvent(StrEnum):
"""Base class for an instance event."""
...
class VibrationInstanceEvent(EventInstanceEvent):
"""Event of a vibration instance."""
TILT = "tilt"
FALL = "fall"
VIBRATION = "vibration"
class OpenInstanceEvent(EventInstanceEvent):
"""Event of a open instance."""
OPENED = "opened"
CLOSED = "closed"
class ButtonInstanceEvent(EventInstanceEvent):
"""Event of a button instance."""
CLICK = "click"
DOUBLE_CLICK = "double_click"
LONG_PRESS = "long_press"
class MotionInstanceEvent(EventInstanceEvent):
"""Event of a motion instance."""
DETECTED = "detected"
NOT_DETECTED = "not_detected"
class SmokeInstanceEvent(EventInstanceEvent):
"""Event of a smoke instance."""
DETECTED = "detected"
NOT_DETECTED = "not_detected"
HIGH = "high"
class GasInstanceEvent(EventInstanceEvent):
"""Event of a gas instance."""
DETECTED = "detected"
NOT_DETECTED = "not_detected"
HIGH = "high"
class BatteryLevelInstanceEvent(EventInstanceEvent):
"""Event of a battery_level instance."""
LOW = "low"
NORMAL = "normal"
HIGH = "high"
class FoodLevelInstanceEvent(EventInstanceEvent):
"""Event of a food_level instance."""
EMPTY = "empty"
LOW = "low"
NORMAL = "normal"
class WaterLevelInstanceEvent(EventInstanceEvent):
"""Event of a water_level instance."""
EMPTY = "empty"
LOW = "low"
NORMAL = "normal"
class WaterLeakInstanceEvent(EventInstanceEvent):
"""Event of a water_leak instance."""
DRY = "dry"
LEAK = "leak"
EventInstanceEventT = TypeVar("EventInstanceEventT", bound=EventInstanceEvent)
def get_event_class_for_instance(instance: EventPropertyInstance) -> type[EventInstanceEvent]:
"""Return EventInstanceEvent enum for event property instance."""
return {
EventPropertyInstance.VIBRATION: VibrationInstanceEvent,
EventPropertyInstance.OPEN: OpenInstanceEvent,
EventPropertyInstance.BUTTON: ButtonInstanceEvent,
EventPropertyInstance.MOTION: MotionInstanceEvent,
EventPropertyInstance.SMOKE: SmokeInstanceEvent,
EventPropertyInstance.GAS: GasInstanceEvent,
EventPropertyInstance.BATTERY_LEVEL: BatteryLevelInstanceEvent,
EventPropertyInstance.FOOD_LEVEL: FoodLevelInstanceEvent,
EventPropertyInstance.WATER_LEVEL: WaterLevelInstanceEvent,
EventPropertyInstance.WATER_LEAK: WaterLeakInstanceEvent,
}[instance]
def get_supported_events_for_instance(instance: EventPropertyInstance) -> list[EventInstanceEvent]:
"""Return list of supported events for event property instance."""
return list(get_event_class_for_instance(instance).__members__.values())
class EventPropertyParameters(APIModel, Generic[EventInstanceEventT]):
"""Parameters of an event property."""
instance: EventPropertyInstance
events: list[dict[Literal["value"], EventInstanceEventT]] = []
@field_validator("events", mode="before")
@classmethod
def set_events(cls, v: Any) -> list[dict[Literal["value"], Any]]:
"""Update events list value."""
if not v:
# Получаем тип события из generic параметра
# В v2 это cls.model_fields["events"].annotation.__args__[1]
event_type = cls.model_fields["events"].annotation.__args__[1]
return [{"value": m} for m in event_type.__members__.values()]
return v
class VibrationEventPropertyParameters(EventPropertyParameters[VibrationInstanceEvent]):
instance: Literal[EventPropertyInstance.VIBRATION] = EventPropertyInstance.VIBRATION
class OpenEventPropertyParameters(EventPropertyParameters[OpenInstanceEvent]):
instance: Literal[EventPropertyInstance.OPEN] = EventPropertyInstance.OPEN
class ButtonEventPropertyParameters(EventPropertyParameters[ButtonInstanceEvent]):
instance: Literal[EventPropertyInstance.BUTTON] = EventPropertyInstance.BUTTON
class MotionEventPropertyParameters(EventPropertyParameters[MotionInstanceEvent]):
instance: Literal[EventPropertyInstance.MOTION] = EventPropertyInstance.MOTION
class SmokeEventPropertyParameters(EventPropertyParameters[SmokeInstanceEvent]):
instance: Literal[EventPropertyInstance.SMOKE] = EventPropertyInstance.SMOKE
class GasEventPropertyParameters(EventPropertyParameters[GasInstanceEvent]):
instance: Literal[EventPropertyInstance.GAS] = EventPropertyInstance.GAS
class BatteryLevelEventPropertyParameters(EventPropertyParameters[BatteryLevelInstanceEvent]):
instance: Literal[EventPropertyInstance.BATTERY_LEVEL] = EventPropertyInstance.BATTERY_LEVEL
class FoodLevelEventPropertyParameters(EventPropertyParameters[FoodLevelInstanceEvent]):
instance: Literal[EventPropertyInstance.FOOD_LEVEL] = EventPropertyInstance.FOOD_LEVEL
class WaterLevelEventPropertyParameters(EventPropertyParameters[WaterLevelInstanceEvent]):
instance: Literal[EventPropertyInstance.WATER_LEVEL] = EventPropertyInstance.WATER_LEVEL
class WaterLeakEventPropertyParameters(EventPropertyParameters[WaterLeakInstanceEvent]):
instance: Literal[EventPropertyInstance.WATER_LEAK] = EventPropertyInstance.WATER_LEAK