zha-toolkit icon indicating copy to clipboard operation
zha-toolkit copied to clipboard

Feature Request: group support in zcl_cmd

Open slyglif opened this issue 1 year ago • 3 comments

It would be really helpful if the zcl_cmd was extended to allow using a zha group / group entity instead of the ieee for the device. My particular use case is wanting to call a command on 10 Inovelli Blue-Series dimmers to set / clear alerts. I tried using the following and unfortunately it returns errors. For reference the group id is 0x0012, but I don't see it mentioned anywhere in the logs, which makes me think zha_toolkit isn't trying to use the underlying group format of zha.issue_zigbee_cluster_command.

data:
  ieee: switch.texas_instruments_cc2652_inovelli_led_notifications
  endpoint: 1
  cluster: 64561
  cmd: 3
  tries: 1
  kwargs:
    led_number: 0
    led_effect: 1
    led_color: 170
    led_level: 100
    led_duration: 1

log messages:

2025-01-06 07:42:19.857 ERROR (MainThread) [custom_components.zha_toolkit.utils] InCluster 0xFC31 not found for '00:12:4b:00:25:7c:a6:5d', endpoint 1
2025-01-06 07:42:19.858 ERROR (MainThread) [custom_components.zha_toolkit] Exception 'InCluster 0xFC31 not found for '00:12:4b:00:25:7c:a6:5d', endpoint 1' for service call with data '{'zha_toolkit_version': 'v1.1.24', 'zigpy_version': '0.73.3', 'zigpy_rf_version': '0.13.1', 'ieee_org': 'switch.texas_instruments_cc2652_inovelli_led_notifications', 'ieee': '00:12:4b:00:25:7c:a6:5d', 'command': 'zcl_cmd', 'command_data': None, 'start_time': '2025-01-06T17:42:19.842297+00:00', 'errors': ['ValueError("InCluster 0xFC31 not found for \'00:12:4b:00:25:7c:a6:5d\', endpoint 1")'], 'params': {'cmd_id': 3, 'endpoint_id': 1, 'cluster_id': 64561, 'dir': 0, 'tries': 1, 'expect_reply': True, 'args': [], 'kwargs': {'led_number': 0, 'led_effect': 1, 'led_color': 170, 'led_level': 100, 'led_duration': 1}, 'read_before_write': True, 'read_after_write': True}, 'success': False}'
2025-01-06 07:42:19.858 ERROR (MainThread) [homeassistant.helpers.script.websocket_api_script] websocket_api script: Error executing script. Unexpected error for call_service at pos 1: InCluster 0xFC31 not found for '00:12:4b:00:25:7c:a6:5d', endpoint 1
Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 526, in _async_step
    await getattr(self, handler)()
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 764, in _async_call_service_step
    response_data = await self._async_run_long_action(
                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    ...<9 lines>...
    )
    ^
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 727, in _async_run_long_action
    return await long_task
           ^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/core.py", line 2795, in async_call
    response_data = await coro
                    ^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/core.py", line 2838, in _execute_service
    return await target(service_call)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/config/custom_components/zha_toolkit/__init__.py", line 833, in toolkit_service
    raise handler_exception
  File "/config/custom_components/zha_toolkit/__init__.py", line 785, in toolkit_service
    handler_result = await handler(
                     ^^^^^^^^^^^^^^
    ...<8 lines>...
    )
    ^
  File "/config/custom_components/zha_toolkit/__init__.py", line 899, in command_handler_default
    return await default.default(
           ^^^^^^^^^^^^^^^^^^^^^^
        app, listener, ieee, cmd, data, service, params, event_data
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
  File "/config/custom_components/zha_toolkit/default.py", line 51, in default
    await handler(app, listener, ieee, cmd, data, service, params, event_data)
  File "/config/custom_components/zha_toolkit/zcl_cmd.py", line 29, in zcl_cmd
    cluster = u.get_cluster_from_params(dev, params, event_data)
  File "/config/custom_components/zha_toolkit/utils.py", line 528, in get_cluster_from_params
    raise ValueError(msg)
ValueError: InCluster 0xFC31 not found for '00:12:4b:00:25:7c:a6:5d', endpoint 1
2025-01-06 07:42:19.873 ERROR (MainThread) [homeassistant.components.websocket_api.http.connection] [546471873840] Error handling message: Unknown error (unknown_error) Administrator from 192.168.33.16 (Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/18.2 Safari/605.1.15)
Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/components/websocket_api/decorators.py", line 28, in _handle_async_response
    await func(hass, connection, msg)
  File "/usr/src/homeassistant/homeassistant/components/websocket_api/commands.py", line 816, in handle_execute_script
    script_result = await script_obj.async_run(
                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^
        msg.get("variables"), context=context
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 1801, in async_run
    return await asyncio.shield(create_eager_task(run.async_run()))
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 464, in async_run
    await self._async_step(log_exceptions=False)
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 528, in _async_step
    self._handle_exception(
    ~~~~~~~~~~~~~~~~~~~~~~^
        ex, continue_on_error, self._log_exceptions or log_exceptions
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 558, in _handle_exception
    raise exception
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 526, in _async_step
    await getattr(self, handler)()
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 764, in _async_call_service_step
    response_data = await self._async_run_long_action(
                    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    ...<9 lines>...
    )
    ^
  File "/usr/src/homeassistant/homeassistant/helpers/script.py", line 727, in _async_run_long_action
    return await long_task
           ^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/core.py", line 2795, in async_call
    response_data = await coro
                    ^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/core.py", line 2838, in _execute_service
    return await target(service_call)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/config/custom_components/zha_toolkit/__init__.py", line 833, in toolkit_service
    raise handler_exception
  File "/config/custom_components/zha_toolkit/__init__.py", line 785, in toolkit_service
    handler_result = await handler(
                     ^^^^^^^^^^^^^^
    ...<8 lines>...
    )
    ^
  File "/config/custom_components/zha_toolkit/__init__.py", line 899, in command_handler_default
    return await default.default(
           ^^^^^^^^^^^^^^^^^^^^^^
        app, listener, ieee, cmd, data, service, params, event_data
        ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    )
    ^
  File "/config/custom_components/zha_toolkit/default.py", line 51, in default
    await handler(app, listener, ieee, cmd, data, service, params, event_data)
  File "/config/custom_components/zha_toolkit/zcl_cmd.py", line 29, in zcl_cmd
    cluster = u.get_cluster_from_params(dev, params, event_data)
  File "/config/custom_components/zha_toolkit/utils.py", line 528, in get_cluster_from_params
    raise ValueError(msg)
ValueError: InCluster 0xFC31 not found for '00:12:4b:00:25:7c:a6:5d', endpoint 1

slyglif avatar Jan 06 '25 17:01 slyglif

The error is that the cluster 0xFC31 is not found for '00:12:4b:00:25:7c:a6:5d', so switch.texas_instruments_cc2652_inovelli_led_notifications was identified as a zigbee object with an IEEE address.

So if that references a group, then this needs to be identifiable (in python) - maybe by checking the entity type in some way.

And once that is done, the destination address must be the group address when sending the command.

mdeweerd avatar Jan 06 '25 18:01 mdeweerd

It's unfortunate that ZHA doesn't make devices for groups and instead just creates sort of a proxy via an entity. The only way I know to tell from an entity if it is a group is to look at the unique_id, which doesn't appear to be available in templating. It does follow a specific format , which seems to be DOMAIN_zha_group_GROUPID ("switch_zha_group_0x0012" is the unique_id for this one, but I have to look in the entity_registry to get that).

slyglif avatar Jan 06 '25 18:01 slyglif

An alternative would be to take a "group" parameter in lieu of "ieee", but that would mean the caller would have to know in advance that they're doing it to a group instead of a direct zha device. It would simplify the code in zha_toolkit though, since the parameters are different for zha.issue_zigbee_cluster_command when it is a group instead of a device.

slyglif avatar Jan 06 '25 22:01 slyglif