Skip to content
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

Zlinky_TIC conversion to quirk v2 #3456

Open
wants to merge 10 commits into
base: dev
Choose a base branch
from
243 changes: 150 additions & 93 deletions zhaquirks/lixee/zlinky.py
Original file line number Diff line number Diff line change
@@ -1,31 +1,46 @@
"""Quirk for ZLinky_TIC."""

from copy import deepcopy

from zigpy.profiles import zgp, zha
from zigpy.quirks import CustomCluster, CustomDevice
import zigpy.types as t
from zigpy.zcl.clusters.general import (
Basic,
GreenPowerProxy,
Identify,
Ota,
PowerConfiguration,
Time,
from zigpy.quirks import CustomCluster
from zigpy.quirks.v2 import EntityPlatform, EntityType, QuirkBuilder
from zigpy.quirks.v2.homeassistant import (
UnitOfApparentPower,
UnitOfElectricCurrent,
UnitOfPower,
)
import zigpy.types as t
from zigpy.zcl.clusters.homeautomation import ElectricalMeasurement, MeterIdentification
from zigpy.zcl.clusters.smartenergy import Metering

from zhaquirks.const import (
DEVICE_TYPE,
ENDPOINTS,
INPUT_CLUSTERS,
MODELS_INFO,
OUTPUT_CLUSTERS,
PROFILE_ID,
)
from zhaquirks.lixee import LIXEE, ZLINKY_MANUFACTURER_CLUSTER_ID
from zhaquirks.tuya import TuyaManufCluster


class ZLinkyTICRelay(t.enum8):
"""ZLinkyTICTarif tarif enumeration."""

Off = 0
On = 1


class ZLinkyTICModeIdentifier(t.enum8):
"""ZLinkyTICTarif tarif enumeration."""

historique_monophase = 0
standard_monophase = 1
historique_triphase = 2
standard_triphase = 3
standard_monophase_producteur = 5
standard_triphase_producteur = 7


class ZLinkyTICTarif(t.enum8):
"""ZLinkyTICTarif tarif enumeration."""

BLEU_HC = 0x01
BLEU_HP = 0x02
BLANC_HC = 0x03
BLANC_HP = 0x04
ROUGE_HC = 0x05
ROUGE_HP = 0x06


class ZLinkyTICManufacturerCluster(CustomCluster):
Expand Down Expand Up @@ -148,79 +163,121 @@ class ZLinkyTICMetering(CustomCluster, Metering):
_CONSTANT_ATTRIBUTES = {MULTIPLIER: 1, DIVISOR: 1000}


class ZLinkyTIC(CustomDevice):
"""ZLinky_TIC from LiXee."""

signature = {
MODELS_INFO: [(LIXEE, "ZLinky_TIC")],
ENDPOINTS: {
1: {
PROFILE_ID: zha.PROFILE_ID,
DEVICE_TYPE: zha.DeviceType.METER_INTERFACE,
INPUT_CLUSTERS: [
Basic.cluster_id,
Identify.cluster_id,
Metering.cluster_id,
MeterIdentification.cluster_id,
ElectricalMeasurement.cluster_id,
ZLinkyTICManufacturerCluster.cluster_id,
],
OUTPUT_CLUSTERS: [Ota.cluster_id],
},
242: {
PROFILE_ID: zgp.PROFILE_ID,
DEVICE_TYPE: zgp.DeviceType.PROXY_BASIC,
INPUT_CLUSTERS: [GreenPowerProxy.cluster_id],
OUTPUT_CLUSTERS: [GreenPowerProxy.cluster_id],
},
},
}
replacement = {
ENDPOINTS: {
1: {
PROFILE_ID: zha.PROFILE_ID,
DEVICE_TYPE: zha.DeviceType.METER_INTERFACE,
INPUT_CLUSTERS: [
Basic.cluster_id,
PowerConfiguration.cluster_id,
Identify.cluster_id,
ZLinkyTICMetering,
MeterIdentification.cluster_id,
ElectricalMeasurement.cluster_id,
ZLinkyTICManufacturerCluster,
],
OUTPUT_CLUSTERS: [Ota.cluster_id],
},
242: {
PROFILE_ID: zgp.PROFILE_ID,
DEVICE_TYPE: zgp.DeviceType.PROXY_BASIC,
INPUT_CLUSTERS: [GreenPowerProxy.cluster_id],
OUTPUT_CLUSTERS: [GreenPowerProxy.cluster_id],
},
},
}


class ZLinkyTICFWV12(ZLinkyTIC):
"""ZLinky_TIC from LiXee with firmware v12.0 & v13.0."""
class ZLinkyTICElectricalMeasurement(CustomCluster, ElectricalMeasurement):
"""ZLinky_TIC custom lectricalMeasurement cluster."""

signature = deepcopy(ZLinkyTIC.signature)
attributes = ElectricalMeasurement.attributes.copy()

# Insert PowerConfiguration cluster in signature for devices with firmware v12.0 & v13.0
signature[ENDPOINTS][1][INPUT_CLUSTERS].insert(1, PowerConfiguration.cluster_id)
attributes[0x0908] = ("rms_current_p2", t.uint16_t, True)
attributes[0x0A08] = ("rms_current_p3", t.uint16_t, True)


class ZLinkyTICFWV14(ZLinkyTICFWV12):
"""ZLinky_TIC from LiXee with firmware v14.0+."""

signature = deepcopy(ZLinkyTICFWV12.signature)
replacement = deepcopy(ZLinkyTICFWV12.replacement)

# Insert Time configuration cluster in signature for devices with firmware v14.0+
signature[ENDPOINTS][1][INPUT_CLUSTERS].insert(1, Time.cluster_id)

# Insert Tuya cluster in signature for devices with firmware v14.0+
signature[ENDPOINTS][1][INPUT_CLUSTERS].insert(7, TuyaManufCluster.cluster_id)
signature[ENDPOINTS][1][OUTPUT_CLUSTERS].insert(1, TuyaManufCluster.cluster_id)

replacement[ENDPOINTS][1][INPUT_CLUSTERS].insert(1, Time.cluster_id)
(
QuirkBuilder(LIXEE, "ZLinky_TIC")
.replaces(ZLinkyTICMetering)
.replaces(ZLinkyTICElectricalMeasurement)
.replaces(ZLinkyTICManufacturerCluster)
.sensor(
ZLinkyTICMetering.AttributeDefs.site_id.name,
ZLinkyTICMetering.cluster_id,
fallback_name="PRN",
translation_key="PRN",
)
.sensor(
MeterIdentification.AttributeDefs.power_threshold.name,
MeterIdentification.cluster_id,
unit=UnitOfApparentPower.VOLT_AMPERE,
fallback_name="Cut-off Power Threshold",
translation_key="power_threshold",
)
.sensor(
ElectricalMeasurement.AttributeDefs.active_power_ph_b.name,
ElectricalMeasurement.cluster_id,
unit=UnitOfPower.WATT,
fallback_name="Active Power Phase 2",
translation_key="active_power_phase_2",
)
.sensor(
ElectricalMeasurement.AttributeDefs.active_power_ph_c.name,
ElectricalMeasurement.cluster_id,
unit=UnitOfPower.WATT,
fallback_name="Active Power Phase 3",
translation_key="active_power_phase_3",
)
.sensor(
ZLinkyTICMetering.AttributeDefs.meter_serial_number.name,
ZLinkyTICMetering.cluster_id,
fallback_name="Serial Number",
translation_key="serial_number",
)
.sensor(
ElectricalMeasurement.AttributeDefs.active_power_max.name,
ElectricalMeasurement.cluster_id,
translation_key="power_max",
unit=UnitOfApparentPower.VOLT_AMPERE,
fallback_name="Max Power",
)
.sensor(
ElectricalMeasurement.AttributeDefs.active_power_max_ph_b.name,
ElectricalMeasurement.cluster_id,
translation_key="power_max",
unit=UnitOfApparentPower.VOLT_AMPERE,
fallback_name="Max Power Phase 2",
)
.sensor(
ElectricalMeasurement.AttributeDefs.active_power_max_ph_c.name,
ElectricalMeasurement.cluster_id,
translation_key="power_max",
unit=UnitOfApparentPower.VOLT_AMPERE,
fallback_name="Max Power Phase 3",
)
.sensor(
ZLinkyTICElectricalMeasurement.AttributeDefs.rms_current.name,
ZLinkyTICElectricalMeasurement.cluster_id,
unit=UnitOfElectricCurrent.AMPERE,
translation_key="current_phase1",
fallback_name="Current Phase 1",
)
.sensor(
ZLinkyTICElectricalMeasurement.AttributeDefs.rms_current_p2.name,
ZLinkyTICElectricalMeasurement.cluster_id,
unit=UnitOfElectricCurrent.AMPERE,
translation_key="current_phase2",
fallback_name="Current Phase 2",
)
.sensor(
ZLinkyTICElectricalMeasurement.AttributeDefs.rms_current_p3.name,
ZLinkyTICElectricalMeasurement.cluster_id,
unit=UnitOfElectricCurrent.AMPERE,
translation_key="current_phase3",
fallback_name="Current Phase 3",
)
.enum(
"std_current_tariff_index_number",
ZLinkyTICTarif,
ZLinkyTICManufacturerCluster.cluster_id,
entity_type=EntityType.STANDARD,
entity_platform=EntityPlatform.SENSOR,
translation_key="Tariff",
fallback_name="Tariff",
)
.enum(
"linky_mode",
ZLinkyTICModeIdentifier,
ZLinkyTICManufacturerCluster.cluster_id,
entity_type=EntityType.STANDARD,
entity_platform=EntityPlatform.SENSOR,
translation_key="linky_mode",
fallback_name="Linky Mode",
)
.enum(
"std_relay",
ZLinkyTICRelay,
ZLinkyTICManufacturerCluster.cluster_id,
entity_type=EntityType.STANDARD,
entity_platform=EntityPlatform.SENSOR,
translation_key="relay_HPHC",
fallback_name="Relay HPHC",
)
.add_to_registry()
)