Nordic Semi nRF52840 chips with ZBOSS Zigbee stack now usable as Zigbee Coordinator for the ZHA integration via new radio library for zigpy

You can now use a Nordic Semiconductor nRF52840 dongle as Zigbee Coordinator radio adaper for the ZHA integration via zigpy-zboss:

https://github.com/kardia-as/zigpy-zboss

Still unofficial and bleeding-edge experimental so need to manually add radio library to ZHA in HA. See:

Should make usable to use either nRF52840 USB dongle or nRF52840 dev kits with correct firmware.

nRF52840 Dongle only costs around $10 USD today:

nRF52840 DK (Development Kit for developers) cost about $60 USD today:

Anyway, ZBOSS Zigbee stack support has the potential to be a big deal since its firmware is open-source and hardware independent:

https://dsr-zoi.com

https://dsr-iot.com

PS: Perhaps more interesting is that if and when this zigpy-zboss library gets developed further then you could be able to use ESP32-C6 / ESP32-H2 SoCs with ESPHome as Zigbee adapter for ZHA:

3 Likes

FYI, @DamKast committed fixes to GitHub - kardia-as/zigpy-zboss and released zigpy-zboss v1.0.2

https://github.com/kardia-as/zigpy-zboss/releases

https://pypi.org/project/zigpy-zboss/

Note that this is still experimental and not yet included in the zha component in Home Assistant core, so if you want to test using an Nordic Semi nRF52840 dongle as a Zigbee Coordinator then you need manually patch directly in the Home Assistant core, modify the source by patching the ZHA component (”zha” under components) inside it to include zigpy-zboss as well as add ”zboss” to the ZHA manifest (manifest.json) as a new radio type, in the same way that the zha component there already includes for example zigpy-znp and ”znp” radio type in ZHA manifest → https://github.com/home-assistant/core/tree/dev/homeassistant/components/zha → https://github.com/home-assistant/core/blob/530556015f98097664d02372701efb15442c6949/homeassistant/components/zha/manifest.json

Alternatively, I believe you can copy the ZHA component and use that as a custom component itself to override the built-in core integration or maybe perhaps even rename it? → Creating your first integration | Home Assistant Developer Docs (a tip, if you try to do that, is to know that the manifest.json file has support for a version key which you could set to a higher version than one that comes with the core and thus it will not overwrite it on updates.

FYI, in related news; noticed grobasoz added some Zigbee CLI/RCP firmware images for ESP32-C6:

ESP ZBOSS 3.0 Libraries (esp-zboss-lib from Espressif) is also based on DSR’s ZBOSS Zigbee stack so if Espressif’s ZBOSS 3.0 Libraries CLI is compatible with the standard ZBOSS CLI then in theory you should be able to make a DIY network-attached remote Zigbee Coordinator adapter setup (i9n a setup similar to Espressif’s new ESP32-H2 + ESP32-C3 combo development board kit) where you have for example ESP32-S3 with ESPHome or Tasmota running serial proxy server and the and it connected to a the ESP32-C6 running only Zigbee CLI firmware so that it just acts as a Zigbee radio adapter when connected via serial using CLI interface.

I have not tested this and again I have no idea if Espressif’s ZBOSS 3.0 Libraries CLI is compatible with the standard ZBOSS CLI So no idea how or if these firmware images from grobasoz would work or not (but grobasoz is at least well known in Home Assisistant’s ZHA community for providing good unofficial Zigbee NCP firmware images for a wide range of Silicon Labs based Zigbee Coordinator adapters).

PS: Espressif also has an earlier two-board ESP Thread Border Router / Zigbee Gateway solution that combined separate ESP32-S3 and ESP32-H2 boards as an example project for reference to achieve a somewhat similar result:

Is there ready to flash firmware available ?

I had to download several gigabytes of software, and google a few hours (because the Nordic Semiconductor documentation is lacking on a few points) just to produce a less then 300k hex file to flash to my nRF52840 to act as a OTBR. But working with HA !

The answer is yes if you are asking about Zigbee NCP (Zigbee Coordinator) firmware for nRF52840.

Link to compiled “nrf-zboss-ncp” hex firmware for nRF52840 USB dongle is in zigpy-zboss readme:

https://github.com/kardia-as/zigpy-zboss/blob/main/README.md#firmware

https://github.com/kardia-as/nrf-zboss-ncp

Alternatively, you can get the very latest unmodified version from the ZBOSS NCP Host example zip:

https://developer.nordicsemi.com/nRF_Connect_SDK/doc/latest/nrf/protocols/zigbee/tools.html#ug-zigbee-tools-ncp-host

https://developer.nordicsemi.com/Zigbee/ncp_sdk_for_host/

You can flash nRF52840 USB dongle using programmer application from the nRF Desktop application

https://www.nordicsemi.com/Products/Development-tools/nrf-connect-for-desktop

1 Like

Great. I have a second one coming, I’ll try it out.

1 Like

Nice, be sure to post any issues to the https://github.com/kardia-as/zigpy-zboss repository on GitHub

Has anyone got this working with ZHA or Z2M?
I have flashed a NRF5284 Dongle with the firmware, and ported usb through VM.

I copied the ZHA folder from Github
Added the folder as /homeassistant/custom_components/zha2

Under manifest.json

  "domain": "zha2",

.........

  "version": "9.2.3",

.........

  "usb": [
    {
        "vid": "2fe3",
        "pid": "0100",
        "description": "ZEPHYR Zigbee NCP",
        "known_devices": "NRF5284 Dongle Coordinator"
    },
................

  "loggers": [
    "zigpy-zboss"

..................

  "requirements": [
    "zigpy-zboss==1.1.2"

Under radio_manager.py

AUTOPROBE_RADIOS = (
    RadioType.zigpy-zboss,
    RadioType.zboss
)

Under const.py

import zigpy_zboss.zigbee.application

.............

class RadioType(enum.Enum):
    """Possible options for radio type."""
    )
    zboss = ("zigpy-zboss = Zigpy-zboss Zigbee radios",
        zigpy_zboss.zigbee.application.ControllerApplication,
        )

When configuring ZHA the dongle is available in Serial Device Path as :
/dev/ttyACM1 - Zigbee NCP, s/n: B0xxxxxxxxxxx4E - ZEPHYR

However, no matter which zigbee radio type I choose it never connects successfully. The Zigpy Zboss RadioType I tried to create is not available as a choice.

Note that this have nothing to do with Zigbee2MQTT (also know as Z2M). This zigpy radio library can only be used with the ZHA integration → https://www.home-assistant.io/integrations/zha/

Since it is still experimental and unofficial so not include by default you should post any quations or requests as new issues to the zigpy-zboss repository on GitHub → Issues · kardia-as/zigpy-zboss · GitHub

I started from scratch, and now it works.

Flashed the NRF52840 dongle with the following firmware https://github.com/kardia-as/nrf-zboss-ncp/blob/38c2e6ffed83ce079212fbaa417daded706faf78/nRF52840_dongle/v2.2.0_ncp_zboss_max_mem.hex

Copied Home Assistants /components/zha to my custom components folder /custom_compontents/zha

Then added a random version key to /custom_compontents/zha/manifest.json

"domain": "zha",
"version": "2023.1.1",

further down in the same manifest.json file, under "requirements": [ , you find a list of packages:
add "zigpy-zboss==1.1.2" to that list.

  "requirements": [
    "zigpy-zboss==1.1.2",
    "bellows==0.36.8",

Then open the file /config/custom_components/zha/core/const.py
Add import zigpy_zboss.zigbee.application

import zigpy_znp.zigbee.application
import zigpy_zboss.zigbee.application

Further down in the same file you will find class RadioType(enum.Enum):
Add boss to it

class RadioType(enum.Enum):
    """Possible options for radio type."""

    ezsp = (
        "EZSP = Silicon Labs EmberZNet protocol: Elelabs, HUSBZB-1, Telegesis",
        bellows.zigbee.application.ControllerApplication,
    )
    boss = ("zigpy-zboss = Zigbee radio",
        zigpy_zboss.zigbee.application.ControllerApplication,
    )

Finally, restart HA.

When you go to “Settings” - “Devices & services” - “Add integration” and search for “Zigbee Home Automation” there should be a package next to it to indicate that it’s a custom integration

image

Using these steps the NRF52840 Dongle now works as an coordinator with ZHA.

1 Like

@stolevegen maybe you care to write step-by-step instructions into ”testing_guide.md” file and submit to the repo for others to follow and update → GitHub - kardia-as/zigpy-zboss

I believe it was mentioned that you if you do nlt also rename your custom copy of the addon in the manifest then you also need to add a distant future date as the version as otherwise it will be overwritten by the official zha integration updates? At least I think someone posted that here → Issues · kardia-as/zigpy-zboss · GitHub

That should be ”zboss” instead of ”boss” :wink:

Would also be great if you or someone else could test and confirm radio migration + backup and restore functionality for zboss radio under zha → ZBOSS Zigbee network backup and network restore + radio migration via zigpy radio API? · Issue #11 · kardia-as/zigpy-zboss · GitHub

That is, test migrating back and forth between diffuradio dongles → https://www.home-assistant.io/integrations/zha/#migrating-to-a-new-zigbee-coordinator-adapter-inside-zha

I wasn’t able to get this to work. What did you put for port speed and flow control?

I’m getting the following error, regardless:

Logger: aiohttp.server
Source: /usr/local/lib/python3.11/site-packages/aiohttp/web_protocol.py:421
First occurred: 13:16:35 (7 occurrences)
Last logged: 13:19:38

Error handling request
Traceback (most recent call last):
  File "/usr/local/lib/python3.11/site-packages/aiohttp/web_protocol.py", line 452, in _handle_request
    resp = await request_handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/site-packages/aiohttp/web_app.py", line 543, in _handle
    resp = await handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/site-packages/aiohttp/web_middlewares.py", line 114, in impl
    return await handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/security_filter.py", line 85, in security_filter_middleware
    return await handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/forwarded.py", line 100, in forwarded_middleware
    return await handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/request_context.py", line 28, in request_context_middleware
    return await handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/ban.py", line 80, in ban_middleware
    return await handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/auth.py", line 233, in auth_middleware
    return await handler(request)
           ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/headers.py", line 31, in headers_middleware
    response = await handler(request)
               ^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/view.py", line 149, in handle
    result = await handler(request, **request.match_info)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/decorators.py", line 63, in with_admin
    return await func(self, request, *args, **kwargs)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/config/config_entries.py", line 177, in post
    return await super().post(request, flow_id)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/components/http/data_validator.py", line 72, in wrapper
    result = await method(view, request, data, *args, **kwargs)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/helpers/data_entry_flow.py", line 110, in post
    result = await self._flow_mgr.async_configure(flow_id, data)
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/data_entry_flow.py", line 320, in async_configure
    result = await self._async_handle_step(
             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/src/homeassistant/homeassistant/data_entry_flow.py", line 416, in _async_handle_step
    result: FlowResult = await getattr(flow, method)(user_input)
                         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/config/custom_components/zha/config_flow.py", line 316, in async_step_verify_radio
    return await self.async_step_choose_formation_strategy()
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/config/custom_components/zha/config_flow.py", line 332, in async_step_choose_formation_strategy
    await self._radio_mgr.async_load_network_settings()
  File "/config/custom_components/zha/radio_manager.py", line 249, in async_load_network_settings
    async with self.connect_zigpy_app() as app:
  File "/usr/local/lib/python3.11/contextlib.py", line 204, in __aenter__
    return await anext(self.gen)
           ^^^^^^^^^^^^^^^^^^^^^
  File "/config/custom_components/zha/radio_manager.py", line 181, in connect_zigpy_app
    app = await self.radio_type.controller.new(
          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/local/lib/python3.11/site-packages/zigpy/application.py", line 242, in new
    app = cls(config)
          ^^^^^^^^^^^
TypeError: Can't instantiate abstract class ControllerApplication with abstract method permit_with_link_key

By default the UART baudrate should be set to 115200 if using firmware from GitHub - kardia-as/nrf-zboss-ncp

Suggest you post a new issue to → GitHub - kardia-as/zigpy-zboss

1 Like

Have done so now. Still not working on latest HA beta.

Developers wanting to assist with this radio library project can help write and submit unit tests for it:

For reference please see tests directory for bellows, zigpy-znp, and zigpy-deconz radio libraries: