Initialize docker stack repo

This commit is contained in:
g4st3r
2026-03-07 17:28:59 +00:00
commit 319d4eeb3e
458 changed files with 67215 additions and 0 deletions

View File

@@ -0,0 +1,260 @@
"""The Polaris IQ Home component."""
from __future__ import annotations
import json
import re
import logging
from typing import Iterable
import copy
from homeassistant.components import mqtt
from homeassistant.components.mqtt.models import ReceiveMessage
from homeassistant.helpers.entity import DeviceInfo, EntityCategory
from homeassistant.util import slugify
from homeassistant.core import HomeAssistant, callback
from homeassistant.config_entries import ConfigEntry
from homeassistant.helpers.entity_platform import AddEntitiesCallback
from .common import PolarisBaseEntity
from homeassistant.util import color as color_util
from homeassistant.components.light import (
DOMAIN,
ATTR_BRIGHTNESS,
ATTR_RGB_COLOR,
ColorMode,
LightEntity,
LightEntityDescription,
)
# Import global values.
from .const import (
MANUFACTURER,
MQTT_ROOT_TOPIC,
DEVICEID,
DEVICETYPE,
POLARIS_DEVICE,
LIGHTS,
LIGHTS_DOUBLE,
PolarisLightEntityDescription,
POLARIS_KETTLE_TYPE,
POLARIS_KETTLE_WITH_WEIGHT_TYPE,
POLARIS_KETTLE_WITH_NIGHT_TYPE,
POLARIS_HUMIDDIFIER_TYPE,
)
_LOGGER = logging.getLogger(__name__)
_LOGGER.setLevel(logging.DEBUG)
async def async_setup_entry(
hass: HomeAssistant, config: ConfigEntry, async_add_entities: AddEntitiesCallback
) -> None:
integrationUniqueID = config.unique_id
mqtt_root = config.data[MQTT_ROOT_TOPIC]
device_id = config.data["DEVICEID"]
device_type = config.data[DEVICETYPE]
device_prefix_topic = config.data["DEVPREFIXTOPIC"]
lightList = []
if device_type in POLARIS_KETTLE_WITH_NIGHT_TYPE:
# Create water heater for kettle devices
LIGHTS_LC = copy.deepcopy(LIGHTS)
for description in LIGHTS_LC:
description.mqttTopicCurrentColor = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCurrentColor}"
description.mqttTopicCommandColor = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCommandColor}"
description.mqttTopicCurrentState = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCurrentState}"
description.mqttTopicCommandState = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCommandState}"
description.device_prefix_topic = device_prefix_topic
lightList.append(
PolarisLight(
description=description,
device_friendly_name=device_id,
mqtt_root=mqtt_root,
device_type=device_type,
device_id=device_id
)
)
if device_type == "835":
# Create humidifier double lights
LIGHTS_DOUBLE_LC = copy.deepcopy(LIGHTS_DOUBLE)
for description in LIGHTS_DOUBLE_LC:
description.mqttTopicCurrentColor = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCurrentColor}"
description.mqttTopicCommandColor = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCommandColor}"
description.mqttTopicCurrentState = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCurrentState}"
description.mqttTopicCommandState = f"{mqtt_root}/{device_prefix_topic}/{description.mqttTopicCommandState}"
description.device_prefix_topic = device_prefix_topic
lightList.append(
PolarisLight(
description=description,
device_friendly_name=device_id,
mqtt_root=mqtt_root,
device_type=device_type,
device_id=device_id
)
)
async_add_entities(lightList, update_before_add=True)
class PolarisLight(PolarisBaseEntity, LightEntity):
entity_description: PolarisLightEntityDescription
def __init__(
self,
device_friendly_name: str,
description: PolarisLightEntityDescription,
mqtt_root: str,
device_id: str | None=None,
device_type: str | None=None,
) -> None:
super().__init__(
device_friendly_name=device_friendly_name,
mqtt_root=mqtt_root,
device_type=device_type,
device_id=device_id,
)
self.entity_description = description
self._attr_unique_id = slugify(f"{device_id}_{description.name}")
self.entity_id = f"{DOMAIN}.{POLARIS_DEVICE[int(device_type)]['class']}_{POLARIS_DEVICE[int(device_type)]['model']}_{description.name}"
self._attr_color_mode = ColorMode.RGB
self._attr_supported_color_modes = {ColorMode.RGB}
self._attr_has_entity_name = True
self._attr_rgb_color = [255, 255, 255]
self._attr_brightness = 100
self._attr_is_on = False
self._attr_available = False
self._double_color = [[255, 255, 255],[255, 255, 255]]
self._double_state = ["0","0"]
async def async_added_to_hass(self):
if self.device_type == "835":
@callback
def message_received_double_state(message):
if message.payload[1] == "0" and self.entity_description.key == "night_up":
self._attr_is_on = False
# self._double_state[0] = "0"
elif message.payload[3] == "0" and self.entity_description.key == "night_down":
self._attr_is_on = False
# self._double_state[1] = "0"
elif message.payload[1] in {"1","2","3"} and self.entity_description.key == "night_up":
self._attr_is_on = True
elif message.payload[3] in {"1","2","3"} and self.entity_description.key == "night_down":
self._attr_is_on = True
else:
self._attr_is_on = None
self._double_state[0] = message.payload[1]
self._double_state[1] = message.payload[3]
rgb_up = color_util.rgb_hex_to_rgb_list(message.payload[4:10])
rgb_down = color_util.rgb_hex_to_rgb_list(message.payload[10:])
self._double_color = [rgb_up, rgb_down]
if self.entity_description.key == "night_up":
rgb = rgb_up
else:
rgb = rgb_down
level = int(max(rgb)/255*100)
self._attr_brightness = level
rgb_color = rgb
bright_factor_old = max(rgb)/255
bright_factor_new = level / 100 / bright_factor_old
self._attr_rgb_color = [int(value / bright_factor_new) for value in rgb_color]
self.async_write_ha_state()
await mqtt.async_subscribe(
self.hass,
self.entity_description.mqttTopicCurrentState,
message_received_double_state,
1,
)
else:
@callback
def message_received_rgb(message):
rgb = color_util.rgb_hex_to_rgb_list(message.payload)
level = int(max(rgb)/255*100)
self._attr_brightness = level
if (self.device_type == "176" or self.device_type == "255"):
rgb_color = [rgb[0], rgb[1], rgb[2]]
else:
rgb_color = rgb
bright_factor_old = max(rgb)/255
bright_factor_new = level / 100 / bright_factor_old
self._attr_rgb_color = [int(value / bright_factor_new) for value in rgb_color]
self.async_write_ha_state()
@callback
def message_received_state(message):
if str(message.payload).lower() in ("1", "true"):
self._attr_is_on = True
elif str(message.payload).lower() in ("0", "false"):
self._attr_is_on = False
else:
self._attr_is_on = None
self.async_write_ha_state()
await mqtt.async_subscribe(
self.hass,
self.entity_description.mqttTopicCurrentColor,
message_received_rgb,
1,
)
await mqtt.async_subscribe(
self.hass,
self.entity_description.mqttTopicCurrentState,
message_received_state,
1,
)
@callback
async def entity_availability(message):
if self.entity_description.name != "available":
if str(message.payload).lower() in ("1", "true"):
self._attr_available = False
else:
self._attr_available = True
self.async_write_ha_state()
await mqtt.async_subscribe(self.hass, f"{self.mqtt_root}/{self.entity_description.device_prefix_topic}/state/error/connection", entity_availability, 1)
async def async_turn_on(self, **kwargs: Any) -> None:
topic = self.entity_description.mqttTopicCommandColor
if ATTR_RGB_COLOR in kwargs:
color = color_util.color_rgb_to_hex(*kwargs[ATTR_RGB_COLOR])
self._attr_rgb_color = color_util.rgb_hex_to_rgb_list(color)
elif ATTR_BRIGHTNESS in kwargs:
level = int((kwargs.get(ATTR_BRIGHTNESS, 100) * 100) / 255)
self._attr_brightness = level
bright_factor_old = max(self._attr_rgb_color)/255
bright_factor_new = self._attr_brightness/ 100 / bright_factor_old
self._attr_rgb_color = [int(value * bright_factor_new) for value in self._attr_rgb_color]
if (self.device_type == "176" or self.device_type == "255"):
mqtt.publish(self.hass, topic, f"{self._attr_rgb_color[0]:02x}{self._attr_rgb_color[1]:02x}{self._attr_rgb_color[2]:02x}00")
elif self.device_type == "835":
if self.entity_description.key == "night_up":
mqtt.publish(self.hass, topic, f"030{self._double_state[1]}{color_util.color_rgb_to_hex(self._attr_rgb_color[0], self._attr_rgb_color[1],self._attr_rgb_color[2])}{self._double_color[1][0]:02x}{self._double_color[1][1]:02x}{self._double_color[1][2]:02x}")
if self.entity_description.key == "night_down":
mqtt.publish(self.hass, topic, f"0{self._double_state[0]}03{self._double_color[0][0]:02x}{self._double_color[0][1]:02x}{self._double_color[0][2]:02x}{color_util.color_rgb_to_hex(self._attr_rgb_color[0], self._attr_rgb_color[1],self._attr_rgb_color[2])}")
else:
mqtt.publish(self.hass, topic, color_util.color_rgb_to_hex(self._attr_rgb_color[0], self._attr_rgb_color[1],self._attr_rgb_color[2]))
if self.device_type != "835":
topic = self.entity_description.mqttTopicCommandState
mqtt.publish(self.hass, topic, "true")
self._attr_is_on = True
async def async_turn_off(self, **kwargs: Any) -> None:
topic = self.entity_description.mqttTopicCommandState
if self.device_type == "835":
if self.entity_description.key == "night_up":
mess = f"000{self._double_state[1]}{self._double_color[0][0]:02x}{self._double_color[0][1]:02x}{self._double_color[0][2]:02x}{self._double_color[1][0]:02x}{self._double_color[1][1]:02x}{self._double_color[1][2]:02x}"
if self.entity_description.key == "night_down":
mess = f"0{self._double_state[0]}00{self._double_color[0][0]:02x}{self._double_color[0][1]:02x}{self._double_color[0][2]:02x}{self._double_color[1][0]:02x}{self._double_color[1][1]:02x}{self._double_color[1][2]:02x}"
mqtt.publish(self.hass, topic, mess)
else:
mqtt.publish(self.hass, topic, "false")
self._attr_is_on = False
@property
def is_on(self) -> bool:
return self._attr_is_on
@property
def brightness(self) -> int:
return int((self._attr_brightness * 255) / 100)
@property
def rgb_color(self) -> tuple[int, int, int] | None:
return self._attr_rgb_color