zha-device-handlers
zha-device-handlers copied to clipboard
[Device Support Request] Add support for Philips Hue Wall Switch RDM004
Problem description
I am encountering an issue with one of my Philips Hue Wall Switches and would appreciate your assistance. Here are the details:
-
Device 1: Philips Hue Wall Switch Model RDM001
- Status: Works perfectly, no issues.
-
Device 2: Philips Hue Wall Switch Model RDM004
- Problem: This device is not identified as a Philips Hue Wall Switch within the system. Consequently, it does not operate as expected.
Solution description
Add support for Philips Hue Wall Switch Model RDM004
Screenshots/Video
Screenshots/Video
Philips Hue Wall Switch Model RDM001, working as expected
Philips Hue Wall Switch Model RDM004, not working
Device signature
Device signature
{
"node_descriptor": "NodeDescriptor(logical_type=<LogicalType.EndDevice: 2>, complex_descriptor_available=0, user_descriptor_available=0, reserved=0, aps_flags=0, frequency_band=<FrequencyBand.Freq2400MHz: 8>, mac_capability_flags=<MACCapabilityFlags.AllocateAddress: 128>, manufacturer_code=4107, maximum_buffer_size=82, maximum_incoming_transfer_size=128, server_mask=11264, maximum_outgoing_transfer_size=128, descriptor_capability_field=<DescriptorCapability.NONE: 0>, *allocate_address=True, *is_alternate_pan_coordinator=False, *is_coordinator=False, *is_end_device=True, *is_full_function_device=False, *is_mains_powered=False, *is_receiver_on_when_idle=False, *is_router=False, *is_security_capable=False)",
"endpoints": {
"1": {
"profile_id": "0x0104",
"device_type": "0x0830",
"input_clusters": [
"0x0000",
"0x0001",
"0x0003",
"0xfc00"
],
"output_clusters": [
"0x0000",
"0x0003",
"0x0004",
"0x0006",
"0x0008",
"0x0019"
]
}
},
"manufacturer": "Signify Netherlands B.V.",
"model": "RDM004",
"class": "zigpy.device.Device"
}
Diagnostic information
Diagnostic information
{
"home_assistant": {
"installation_type": "Home Assistant OS",
"version": "2023.11.2",
"dev": false,
"hassio": true,
"virtualenv": false,
"python_version": "3.11.6",
"docker": true,
"arch": "aarch64",
"timezone": "Europe/Paris",
"os_name": "Linux",
"os_version": "6.1.21-v8",
"supervisor": "2023.11.3",
"host_os": "Home Assistant OS 11.1",
"docker_version": "24.0.6",
"chassis": "embedded",
"run_as_root": true
},
"custom_components": {
"hacs": {
"version": "1.33.0",
"requirements": [
"aiogithubapi>=22.10.1"
]
}
},
"integration_manifest": {
"domain": "zha",
"name": "Zigbee Home Automation",
"after_dependencies": [
"onboarding",
"usb"
],
"codeowners": [
"@dmulcahey",
"@adminiuga",
"@puddly"
],
"config_flow": true,
"dependencies": [
"file_upload"
],
"documentation": "https://www.home-assistant.io/integrations/zha",
"iot_class": "local_polling",
"loggers": [
"aiosqlite",
"bellows",
"crccheck",
"pure_pcapy3",
"zhaquirks",
"zigpy",
"zigpy_deconz",
"zigpy_xbee",
"zigpy_zigate",
"zigpy_znp",
"universal_silabs_flasher"
],
"requirements": [
"bellows==0.36.8",
"pyserial==3.5",
"pyserial-asyncio==0.6",
"zha-quirks==0.0.106",
"zigpy-deconz==0.21.1",
"zigpy==0.59.0",
"zigpy-xbee==0.19.0",
"zigpy-zigate==0.11.0",
"zigpy-znp==0.11.6",
"universal-silabs-flasher==0.0.14",
"pyserial-asyncio-fast==0.11"
],
"usb": [
{
"vid": "10C4",
"pid": "EA60",
"description": "*2652*",
"known_devices": [
"slae.sh cc2652rb stick"
]
},
{
"vid": "1A86",
"pid": "55D4",
"description": "*sonoff*plus*",
"known_devices": [
"sonoff zigbee dongle plus v2"
]
},
{
"vid": "10C4",
"pid": "EA60",
"description": "*sonoff*plus*",
"known_devices": [
"sonoff zigbee dongle plus"
]
},
{
"vid": "10C4",
"pid": "EA60",
"description": "*tubeszb*",
"known_devices": [
"TubesZB Coordinator"
]
},
{
"vid": "1A86",
"pid": "7523",
"description": "*tubeszb*",
"known_devices": [
"TubesZB Coordinator"
]
},
{
"vid": "1A86",
"pid": "7523",
"description": "*zigstar*",
"known_devices": [
"ZigStar Coordinators"
]
},
{
"vid": "1CF1",
"pid": "0030",
"description": "*conbee*",
"known_devices": [
"Conbee II"
]
},
{
"vid": "10C4",
"pid": "8A2A",
"description": "*zigbee*",
"known_devices": [
"Nortek HUSBZB-1"
]
},
{
"vid": "0403",
"pid": "6015",
"description": "*zigate*",
"known_devices": [
"ZiGate+"
]
},
{
"vid": "10C4",
"pid": "EA60",
"description": "*zigate*",
"known_devices": [
"ZiGate"
]
},
{
"vid": "10C4",
"pid": "8B34",
"description": "*bv 2010/10*",
"known_devices": [
"Bitron Video AV2010/10"
]
}
],
"zeroconf": [
{
"type": "_esphomelib._tcp.local.",
"name": "tube*"
},
{
"type": "_zigate-zigbee-gateway._tcp.local.",
"name": "*zigate*"
},
{
"type": "_zigstar_gw._tcp.local.",
"name": "*zigstar*"
},
{
"type": "_uzg-01._tcp.local.",
"name": "uzg-01*"
},
{
"type": "_slzb-06._tcp.local.",
"name": "slzb-06*"
}
],
"is_built_in": true
},
"data": {
"ieee": "**REDACTED**",
"nwk": 2733,
"manufacturer": "Signify Netherlands B.V.",
"model": "RDM004",
"name": "Signify Netherlands B.V. RDM004",
"quirk_applied": false,
"quirk_class": "zigpy.device.Device",
"quirk_id": null,
"manufacturer_code": 4107,
"power_source": "Battery or Unknown",
"lqi": 184,
"rssi": -54,
"last_seen": "2023-11-19T00:35:42",
"available": true,
"device_type": "EndDevice",
"signature": {
"node_descriptor": "NodeDescriptor(logical_type=<LogicalType.EndDevice: 2>, complex_descriptor_available=0, user_descriptor_available=0, reserved=0, aps_flags=0, frequency_band=<FrequencyBand.Freq2400MHz: 8>, mac_capability_flags=<MACCapabilityFlags.AllocateAddress: 128>, manufacturer_code=4107, maximum_buffer_size=82, maximum_incoming_transfer_size=128, server_mask=11264, maximum_outgoing_transfer_size=128, descriptor_capability_field=<DescriptorCapability.NONE: 0>, *allocate_address=True, *is_alternate_pan_coordinator=False, *is_coordinator=False, *is_end_device=True, *is_full_function_device=False, *is_mains_powered=False, *is_receiver_on_when_idle=False, *is_router=False, *is_security_capable=False)",
"endpoints": {
"1": {
"profile_id": "0x0104",
"device_type": "0x0830",
"input_clusters": [
"0x0000",
"0x0001",
"0x0003",
"0xfc00"
],
"output_clusters": [
"0x0000",
"0x0003",
"0x0004",
"0x0006",
"0x0008",
"0x0019"
]
}
},
"manufacturer": "Signify Netherlands B.V.",
"model": "RDM004"
},
"active_coordinator": false,
"entities": [
{
"entity_id": "sensor.test_switch_battery",
"name": "Signify Netherlands B.V. RDM004"
},
{
"entity_id": "button.test_switch_identify",
"name": "Signify Netherlands B.V. RDM004"
}
],
"neighbors": [],
"routes": [],
"endpoint_names": [
{
"name": "NON_COLOR_SCENE_CONTROLLER"
}
],
"user_given_name": "Test Switch",
"device_reg_id": "5e45b4468f3122dc3e685d098fd61626",
"area_id": null,
"cluster_details": {
"1": {
"device_type": {
"name": "NON_COLOR_SCENE_CONTROLLER",
"id": 2096
},
"profile_id": 260,
"in_clusters": {
"0x0000": {
"endpoint_attribute": "basic",
"attributes": {
"0x0004": {
"attribute_name": "manufacturer",
"value": "Signify Netherlands B.V."
},
"0x0005": {
"attribute_name": "model",
"value": "RDM004"
}
},
"unsupported_attributes": {}
},
"0x0001": {
"endpoint_attribute": "power",
"attributes": {
"0x0021": {
"attribute_name": "battery_percentage_remaining",
"value": 200
},
"0x0020": {
"attribute_name": "battery_voltage",
"value": 31
}
},
"unsupported_attributes": {
"0x0033": {
"attribute_name": "battery_quantity"
},
"0x0031": {
"attribute_name": "battery_size"
}
}
},
"0x0003": {
"endpoint_attribute": "identify",
"attributes": {},
"unsupported_attributes": {}
},
"0xfc00": {
"endpoint_attribute": "manufacturer_specific",
"attributes": {},
"unsupported_attributes": {}
}
},
"out_clusters": {
"0x0019": {
"endpoint_attribute": "ota",
"attributes": {},
"unsupported_attributes": {}
},
"0x0000": {
"endpoint_attribute": "basic",
"attributes": {},
"unsupported_attributes": {}
},
"0x0003": {
"endpoint_attribute": "identify",
"attributes": {},
"unsupported_attributes": {}
},
"0x0004": {
"endpoint_attribute": "groups",
"attributes": {},
"unsupported_attributes": {}
},
"0x0006": {
"endpoint_attribute": "on_off",
"attributes": {},
"unsupported_attributes": {}
},
"0x0008": {
"endpoint_attribute": "level",
"attributes": {},
"unsupported_attributes": {}
}
}
}
}
}
}
Logs
Logs
[Paste the logs here]
Custom quirk
Custom quirk
[Paste your custom quirk here]
Additional information
No response
got it working with the custom quirk
"""Signify RDM004 device."""
import logging
from typing import Any, List, Optional, Union
from zigpy.profiles import zha
from zigpy.quirks import CustomCluster, CustomDevice
import zigpy.types as t
from zigpy.zcl import foundation
from zigpy.zcl.clusters.general import (
Basic,
Groups,
Identify,
LevelControl,
OnOff,
Ota,
PowerConfiguration,
)
from zhaquirks.const import (
ARGS,
BUTTON,
COMMAND,
COMMAND_ID,
DEVICE_TYPE,
DOUBLE_PRESS,
ENDPOINTS,
INPUT_CLUSTERS,
LONG_PRESS,
LONG_RELEASE,
MODELS_INFO,
OUTPUT_CLUSTERS,
PRESS_TYPE,
PROFILE_ID,
QUADRUPLE_PRESS,
QUINTUPLE_PRESS,
RIGHT,
SHORT_PRESS,
SHORT_RELEASE,
TRIPLE_PRESS,
TURN_ON,
ZHA_SEND_EVENT,
)
from zhaquirks.philips import PHILIPS, SIGNIFY
DEVICE_SPECIFIC_UNKNOWN = 64512
_LOGGER = logging.getLogger(__name__)
class PhilipsBasicCluster(CustomCluster, Basic):
"""Philips Basic cluster."""
attributes = Basic.attributes.copy()
attributes.update(
{
0x0031: ("philips", t.bitmap16, True),
0x0034: ("mode", t.enum8, True),
}
)
attr_config = {0x0031: 0x000B, 0x0034: 0x02}
async def bind(self):
"""Bind cluster."""
result = await super().bind()
await self.write_attributes(self.attr_config, manufacturer=0x100B)
return result
class PhilipsRemoteCluster(CustomCluster):
"""Philips remote cluster."""
cluster_id = 64512
name = "PhilipsRemoteCluster"
ep_attribute = "philips_remote_cluster"
client_commands = {
0x00: foundation.ZCLCommandDef(
"notification",
{
"param1": t.uint8_t,
"param2": t.uint24_t,
"param3": t.uint8_t,
"param4": t.uint8_t,
"param5": t.uint8_t,
"param6": t.uint8_t,
},
is_manufacturer_specific=True,
direction=foundation.Direction.Server_to_Client,
)
}
BUTTONS = {
1: "left",
2: "right",
}
PRESS_TYPES = {0: "press", 1: "hold", 2: "press_release", 3: "hold_release"}
def handle_cluster_request(
self,
hdr: foundation.ZCLHeader,
args: List[Any],
*,
dst_addressing: Optional[
Union[t.Addressing.Group, t.Addressing.IEEE, t.Addressing.NWK]
] = None,
):
"""Handle the cluster command."""
_LOGGER.debug(
"PhilipsRemoteCluster - handle_cluster_request tsn: [%s] command id: %s - args: [%s]",
hdr.tsn,
hdr.command_id,
args,
)
button = self.BUTTONS.get(args[0], args[0])
press_type = self.PRESS_TYPES.get(args[2], args[2])
event_args = {
BUTTON: button,
PRESS_TYPE: press_type,
COMMAND_ID: hdr.command_id,
ARGS: args,
}
action = f"{button}_{press_type}"
self.listener_event(ZHA_SEND_EVENT, action, event_args)
class PhilipsROM004(CustomDevice):
"""Philips ROM004 device."""
signature = {
# <SimpleDescriptor endpoint=1 profile=260 device_type=2080
# device_version=1
# input_clusters=[0, 1, 3, 64512]
# output_clusters=[3, 4, 6, 8, 25]>
MODELS_INFO: [(PHILIPS, "RDM004"), (SIGNIFY, "RDM004")],
ENDPOINTS: {
1: {
PROFILE_ID: zha.PROFILE_ID,
DEVICE_TYPE: zha.DeviceType.NON_COLOR_SCENE_CONTROLLER,
INPUT_CLUSTERS: [
Basic.cluster_id,
PowerConfiguration.cluster_id,
Identify.cluster_id,
DEVICE_SPECIFIC_UNKNOWN,
],
OUTPUT_CLUSTERS: [
Basic.cluster_id,
Identify.cluster_id,
Groups.cluster_id,
OnOff.cluster_id,
LevelControl.cluster_id,
Ota.cluster_id,
],
}
},
}
replacement = {
ENDPOINTS: {
1: {
PROFILE_ID: zha.PROFILE_ID,
DEVICE_TYPE: zha.DeviceType.NON_COLOR_CONTROLLER,
INPUT_CLUSTERS: [
PhilipsBasicCluster,
PowerConfiguration.cluster_id,
Identify.cluster_id,
PhilipsRemoteCluster,
],
OUTPUT_CLUSTERS: [
Ota.cluster_id,
Identify.cluster_id,
Groups.cluster_id,
OnOff.cluster_id,
LevelControl.cluster_id,
],
}
}
}
device_automation_triggers = {
(SHORT_PRESS, TURN_ON): {COMMAND: "left_press"},
(LONG_PRESS, TURN_ON): {COMMAND: "left_hold"},
(DOUBLE_PRESS, TURN_ON): {COMMAND: "left_double_press"},
(TRIPLE_PRESS, TURN_ON): {COMMAND: "left_triple_press"},
(QUADRUPLE_PRESS, TURN_ON): {COMMAND: "left_quadruple_press"},
(QUINTUPLE_PRESS, TURN_ON): {COMMAND: "left_quintuple_press"},
(SHORT_RELEASE, TURN_ON): {COMMAND: "left_short_release"},
(LONG_RELEASE, TURN_ON): {COMMAND: "left_long_release"},
(SHORT_PRESS, RIGHT): {COMMAND: "right_press"},
(LONG_PRESS, RIGHT): {COMMAND: "right_hold"},
(DOUBLE_PRESS, RIGHT): {COMMAND: "right_double_press"},
(TRIPLE_PRESS, RIGHT): {COMMAND: "right_triple_press"},
(QUADRUPLE_PRESS, RIGHT): {COMMAND: "right_quadruple_press"},
(QUINTUPLE_PRESS, RIGHT): {COMMAND: "right_quintuple_press"},
(SHORT_RELEASE, RIGHT): {COMMAND: "right_short_release"},
(LONG_RELEASE, RIGHT): {COMMAND: "right_long_release"},
}
If the RDM004 is compatible with the old RDM001(?) then could just add as an additional signature to exising rdm001.py
quirk:
https://github.com/zigpy/zha-device-handlers/blob/dev/zhaquirks/philips/rdm001.py
For reference also see this related zigbee-herdsman-converters discussion mentioning old 929003017102 and new 9290030171A:
https://github.com/Koenkk/zigbee-herdsman-converters/issues/6269
agree with this ticket. Same behaviour at my instance with the RDM004 Philips / Signify. RDM001 works just fine. I don't see any button triggers with this device in HAOS.
Quirk seems to work. Thanks @VEBERArnaud !
I hope this can be added to the ZHA-library soon. I don't get the custom quirk to work. Specific the second button on my RDM004 doesn't work. I should change the mode 3 - double push button type switch
, but I can't find that option (0x0034) in ZHA.
Anyone already found the setting to change the mode? '0x0034' or 'mode' doesn't appear in my list of clusters and attributes.
Quirk works for me, thanks! :)
I got the same problem. Can anyone maby give me a short description where i can import that given code to?
See here for detailed instructions on adding a custom quirk: https://community.home-assistant.io/t/how-to-configure-the-philips-hue-wall-module-to-use-push-button-momentary-type-wall-switches-zha/451125/27