From 958731616796e7a0f90a507dc3bd5edc665f3b19 Mon Sep 17 00:00:00 2001 From: ecspiegel <87676266+ecspiegel@users.noreply.github.com> Date: Wed, 2 Jul 2025 13:23:36 -0400 Subject: [PATCH 001/130] Clarified MFA requirements for alexa devices (#39812) Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com> --- source/_integrations/alexa_devices.markdown | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/source/_integrations/alexa_devices.markdown b/source/_integrations/alexa_devices.markdown index c49c7b40a99..43377cf817f 100644 --- a/source/_integrations/alexa_devices.markdown +++ b/source/_integrations/alexa_devices.markdown @@ -38,11 +38,11 @@ There is support for the following device families within Home Assistant: - **Amazon Fire TV Stick** - **Amazon Fire Tablet** -and all 3rd party that has Alexa capabilities built-in +- **Third-party devices** with built-in Alexa capabilities. {% warning %} -Currently, only MFA-protected Amazon accounts via the authenticator app are supported. +This integration requires multifactor authentication using an authentication app (such as Microsoft Authenticator, for example). To enable MFA, in your Amazon account settings select **Login & Security** > **2-step verification** > **Backup methods** > **Add new app**. See [Amazon's documentation](https://www.amazon.com/gp/help/customer/display.html?nodeId=G9MX9LXNWXFKMJYU) for more information. {% endwarning %} From 1c6e3e0b7054c8db7d2ce8a8324bafd57a687c67 Mon Sep 17 00:00:00 2001 From: ecspiegel <87676266+ecspiegel@users.noreply.github.com> Date: Thu, 3 Jul 2025 01:46:30 -0400 Subject: [PATCH 002/130] Update rpi_camera.markdown (#39815) Co-authored-by: c0ffeeca7 <38767475+c0ffeeca7@users.noreply.github.com> --- source/_integrations/rpi_camera.markdown | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/source/_integrations/rpi_camera.markdown b/source/_integrations/rpi_camera.markdown index 23e065608d6..07c1348278f 100644 --- a/source/_integrations/rpi_camera.markdown +++ b/source/_integrations/rpi_camera.markdown @@ -15,7 +15,7 @@ related: ha_quality_scale: legacy --- -The `rpi_camera` {% term integration %} allows you to integrate the Raspberry Pi camera into Home Assistant. This integration uses the application [`raspistill`](https://www.raspberrypi.org/documentation/usage/camera/raspicam/raspistill.md) to store the image from camera. +The `rpi_camera` {% term integration %} allows you to integrate the Raspberry Pi camera into Home Assistant. This integration uses the application [`rpicam-still`](https://www.raspberrypi.com/documentation/computers/camera_software.html#rpicam-still) to store the image from camera. {% important %} This integration is only available on Home Assistant Core installation types. Unfortunately, it cannot be used with Home Assistant OS, Supervised or Container. @@ -31,7 +31,7 @@ To enable this camera in your installation, add the following to your {% term "` rpi_camera: ``` -The whole set of configuration variables is documented here [`Raspberry Pi Camera Module - Raspberry Pi Documentation`](https://www.raspberrypi.org/documentation/raspbian/applications/camera.md). +The whole set of configuration variables is documented in the [Raspberry Pi documentation of the camera software](https://www.raspberrypi.com/documentation/computers/camera_software.html#rpicam-still). They are not all wrapped by this `rpi_camera` platform. {% configuration %} From 0b5bfc14a2d5762a1ae3f848eec5c375fa8c73b9 Mon Sep 17 00:00:00 2001 From: ecspiegel <87676266+ecspiegel@users.noreply.github.com> Date: Thu, 3 Jul 2025 01:50:50 -0400 Subject: [PATCH 003/130] Update proxmoxve.markdown (#39816) --- source/_integrations/proxmoxve.markdown | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/source/_integrations/proxmoxve.markdown b/source/_integrations/proxmoxve.markdown index 3128058d357..0d72e9b3d75 100644 --- a/source/_integrations/proxmoxve.markdown +++ b/source/_integrations/proxmoxve.markdown @@ -145,6 +145,10 @@ For the group to access the VMs we need to grant it the auditor role Creating a dedicated user for Home Assistant, limited to only to the access just created is the most secure method. These instructions use the `pve` realm for the user. This allows a connection, but ensures that the user is not authenticated for SSH connections. If you use the `pve` realm, just be sure to add `realm: pve` to your configuration. +{% important %} +The Home Assistant user you create must already exist on the Linux system. +{% endimportant %} + 1. Click `Datacenter` 2. Open `Permissions` and click `Users` 3. Click `Add` From 81aca7c49ae94898187e745cde77775f2f31b41a Mon Sep 17 00:00:00 2001 From: alawadhi3000 <5523980+alawadhi3000@users.noreply.github.com> Date: Thu, 3 Jul 2025 10:02:28 +0300 Subject: [PATCH 004/130] Update gree.markdown (#39817) --- source/_integrations/gree.markdown | 1 + 1 file changed, 1 insertion(+) diff --git a/source/_integrations/gree.markdown b/source/_integrations/gree.markdown index 01ec11caaae..f5c61277194 100644 --- a/source/_integrations/gree.markdown +++ b/source/_integrations/gree.markdown @@ -40,6 +40,7 @@ Any Gree Smart device working with the Gree+ app should be supported, including - Heiwa - Ekokai - Lessar +- Tosot ## Climate From 47832ad5c961ac127a91d87990d404e900a19cf5 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 3 Jul 2025 09:21:15 +0200 Subject: [PATCH 005/130] build(deps-dev): bump sorbet-runtime from 0.5.12216 to 0.5.12219 (#39819) Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- Gemfile.lock | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Gemfile.lock b/Gemfile.lock index e0890044666..cc3e027588e 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -159,7 +159,7 @@ GEM rack-protection (= 4.1.1) rack-session (>= 2.0.0, < 3) tilt (~> 2.0) - sorbet-runtime (0.5.12216) + sorbet-runtime (0.5.12219) stringex (2.8.6) terminal-table (3.0.2) unicode-display_width (>= 1.1.1, < 3) From 4a552ecc13babf2a297893a6cefff1dd131a35ad Mon Sep 17 00:00:00 2001 From: Franck Nijhof Date: Thu, 3 Jul 2025 09:26:42 +0200 Subject: [PATCH 006/130] Add API key permissions requirements to Immich docs (#39820) --- source/_integrations/immich.markdown | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/source/_integrations/immich.markdown b/source/_integrations/immich.markdown index 62db398e47b..98bf69e1310 100644 --- a/source/_integrations/immich.markdown +++ b/source/_integrations/immich.markdown @@ -26,6 +26,10 @@ This integration allows adding an [Immich](https://immich.app/) user account to You need to [obtain the API key](https://immich.app/docs/features/command-line-interface#obtain-the-api-key) for your user account in your Immich instance. +### API key permissions + +For full functionality, enable the `album.read` permission when creating your API key. Without this permission, the media source integration will not work, but all monitoring sensors will continue to function normally. + {% include integrations/config_flow.md %} {% configuration_basic %} From 550c77f350855fd6db20a125caa3043bef502d01 Mon Sep 17 00:00:00 2001 From: Marcel van der Veldt Date: Thu, 3 Jul 2025 09:52:47 +0200 Subject: [PATCH 007/130] Some textual changes to Music Assistant docs (#39814) Co-authored-by: c0ffeeca7 <38767475+c0ffeeca7@users.noreply.github.com> --- source/_integrations/music_assistant.markdown | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/source/_integrations/music_assistant.markdown b/source/_integrations/music_assistant.markdown index 0f6595d2bd4..31cd6b7decd 100644 --- a/source/_integrations/music_assistant.markdown +++ b/source/_integrations/music_assistant.markdown @@ -20,8 +20,10 @@ The **Music Assistant** (MA) {% term integration %} allows you to connect Home A There is currently support for the following Home Assistant Platforms: -- [Media player](#media-player) +- [Media player](#media-player-entities) - [Button](#favorite-current-song-button) + + All of the Home Assistant [Media Player Control Actions](https://www.home-assistant.io/integrations/media_player/#media-control-actions) are supported. The `media_content_id` payload for `media_player.play_media` can be any of the following: @@ -51,7 +53,7 @@ The Music Assistant integration creates media player entities for all players an ### Favorite current song button -The Music Assistant integration creates a button entity for each player to favorite the current song. Pressing this button (manually or by automation) adds the current song to your Music Assistant favorites. This works for local playing songs and tracks from streaming providers. It also works with remote content such as Spotify Connect, AirPlay, or a radio station, as long as the external source provides an artist and title combination (and optionally the album). Note that the button will be marked as unavailable if there is no content playable that could be favorited. +The Music Assistant integration creates a button entity for each player to favorite the current song. Pressing this button (manually or by automation) adds the current song to your Music Assistant favorites. This works for songs stored locally as well as for tracks from streaming providers. It also works with remote content such as Spotify Connect, AirPlay, or a radio station, as long as the external source provides an artist and title combination (and optionally the album). ## Actions From 4c88ebdf6c7a3454c92a9dc1e9669e455cd0354b Mon Sep 17 00:00:00 2001 From: staticdev Date: Thu, 3 Jul 2025 10:04:21 +0200 Subject: [PATCH 008/130] Add mandatory field for WoL integration on example (#39813) --- source/_integrations/wake_on_lan.markdown | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/_integrations/wake_on_lan.markdown b/source/_integrations/wake_on_lan.markdown index 697864cdc54..9ecd40b3a25 100644 --- a/source/_integrations/wake_on_lan.markdown +++ b/source/_integrations/wake_on_lan.markdown @@ -151,7 +151,7 @@ from Home Assistant running on another Linux computer (the **server**). switch: - platform: wake_on_lan name: "TARGET" - ... + mac: XX:XX:XX:XX:XX:XX turn_off: action: shell_command.turn_off_TARGET From fba1515d2b2b5fa4e98d39940cec974c4c76d347 Mon Sep 17 00:00:00 2001 From: tronikos Date: Thu, 3 Jul 2025 01:30:00 -0700 Subject: [PATCH 009/130] Improve docs of Android TV Remote (#39821) --- source/_integrations/androidtv_remote.markdown | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/source/_integrations/androidtv_remote.markdown b/source/_integrations/androidtv_remote.markdown index a1a0fe40951..a70a91b33b2 100644 --- a/source/_integrations/androidtv_remote.markdown +++ b/source/_integrations/androidtv_remote.markdown @@ -31,6 +31,8 @@ For a quick introduction on how to get started with Android TV Remote, check out {% configuration_basic %} Configure Applications List: description: Here you can define applications where the keys are app IDs and the values are app names and icons that will be displayed in the UI. +Enable IME: + description: Enable this option to be able to get the current app name and send text as keyboard input. Disable it for devices that show 'Use keyboard on mobile device screen' instead of the on-screen keyboard. {% endconfiguration_basic %} ## Media player @@ -581,3 +583,8 @@ cards: - If you are not able to connect to the Android TV device, or are asked to pair it again and again, try force-stopping the Android TV Remote Service and clearing its storage. On the Android TV device, go to **Settings** > **Apps** > **Show system apps**. Then, select **Android TV Remote Service** > **Storage** > **Clear storage**. You will have to pair again. - Some onscreen keyboards enabled by TV manufacturers do not support concurrent virtual and onscreen keyboard use. This presents whenever a text field is selected, such as "search" where a constant **use the keyboard on your mobile device** will show, preventing you from opening the onscreen keyboard to type. This can be overcome by either disabling your 3rd party keyboard and using the default Gboard keyboard or by deselecting **Enable IME** in the **Configure** page of the integration. - If you can't turn on your Nvidia Shield device, go to **Settings** > **Remotes & accessories** > **Simplified wake buttons** and disable the following options: **SHIELD 2019 Remote: Wake on power and Netflix buttons only** and **Controllers: Wake on NVIDIA or logo buttons only**. + + +## Removing the integration + +{% include integrations/remove_device_service.md %} From 62b143aa480884ca1d9356831a17df32b330f5bd Mon Sep 17 00:00:00 2001 From: c0ffeeca7 <38767475+c0ffeeca7@users.noreply.github.com> Date: Thu, 3 Jul 2025 10:30:23 +0200 Subject: [PATCH 010/130] Z-Wave terminology: change controller to adapter (#39805) Co-authored-by: AlCalzone Co-authored-by: Martin Hjelmare --- source/_integrations/zwave_js.markdown | 154 +++++++++++++------------ 1 file changed, 79 insertions(+), 75 deletions(-) diff --git a/source/_integrations/zwave_js.markdown b/source/_integrations/zwave_js.markdown index 290fd2e1d89..4c728351cce 100644 --- a/source/_integrations/zwave_js.markdown +++ b/source/_integrations/zwave_js.markdown @@ -50,7 +50,7 @@ The **Z-Wave** {% term integration %} allows you to control a Z-Wave network fro ## Device compatibility -You do not need a Z-Wave controller that is specifically designed for the Z-Wave integration in Home Assistant. The Z-Wave integration in Home Assistant can be operated with any Z-Wave network with other Z-Wave certified devices from other manufacturers. All mains operated nodes within the network will act as repeaters regardless of vendor to increase reliability of the network. +You do not need a Z-Wave adapter that is specifically designed for the Z-Wave integration in Home Assistant. The Z-Wave integration in Home Assistant can be operated with any Z-Wave network with other Z-Wave certified devices from other manufacturers. All mains operated nodes within the network will act as repeaters regardless of vendor to increase reliability of the network. ## Getting started @@ -60,14 +60,15 @@ This sections shows you how to set up a Z-Wave JS server and how to add your fir Throughout this documentation, Home Assistant terminology is used. For some of the concepts, the terminology does not correspond to the terminology used in Z-Wave documentation. The table below provides equivalents for some of those terms. -| Z-Wave functionality | Home Assistant | Definition | -| -------------------- | ------------------------------------------------------ | ----------------------------------------------------------------------------------------------------------- | -| inclusion | add | The process of adding a node to the Z-Wave network | -| exclusion | remove | The process of removing a node from the Z-Wave network | -| replication | copy (not supported in Home Assistant) | The process of copying network information from one controller to another. Not supported in Home Assistant. | -| barrier operator | cover | -| window covering | cover | -| multilevel switch | represented by different entity types: light, fan etc. | +| Z-Wave functionality | Home Assistant | Definition | +| -------------------- | -------------- | ---------- | +| barrier operator | cover | | +| controller | adapter, when referring to the hardware device that provides the Z-Wave functionality. The term controller is still used when referring to the network role (such as primary, secondary controller) | | +| exclusion | remove | The process of removing a node from the Z-Wave network | +| inclusion | add | The process of adding a node to the Z-Wave network | +| multilevel switch | represented by different entity types: light, fan etc. | | +| replication | copy (not supported in Home Assistant) | The process of copying network information from one adapter to another. Not supported in Home Assistant. | +| window covering | cover | | #### Classic inclusion versus SmartStart @@ -81,7 +82,7 @@ For more Z-Wave term definitions, refer to the [terminology section](#z-wave-ter To run a Z-Wave network, you need the following elements: -- A [supported Z-Wave controller](/docs/z-wave/controllers/#supported-z-wave-usb-sticks--hardware-modules). First-time user? For recommendations on what to buy, go [here](#which-z-wave-controller-should-i-buy). +- A [supported Z-Wave adapter](/docs/z-wave/controllers/#supported-z-wave-usb-sticks--hardware-modules). First-time user? For recommendations on what to buy, go [here](#which-z-wave-adapter-should-i-buy). - A running [Z-Wave JS server](#setting-up-a-z-wave-js-server). - An installed Z-Wave integration in Home Assistant. @@ -94,12 +95,12 @@ For other ways to setup a Z-Wave server, refer to the [advanced installation ins Follow these steps: 1. Open the Home Assistant user interface. -2. Plug the Z-Wave dongle into the device running Home Assistant. - - Most likely, your dongle will be recognized automatically. +2. Plug the Z-Wave adapter into the device running Home Assistant. + - Most likely, your adapter will be recognized automatically. - In the dialog, select **Recommended installation**. - This will install the Z-Wave JS add-on on the Home Assistant server. - Add the device to an {% term area %} and select **Finish**. - - **Troubleshooting**: If your dongle is not recognized, follow these steps: + - **Troubleshooting**: If your adapter is not recognized, follow these steps: {% details "Manual setup steps" %} Use this My button: @@ -118,15 +119,15 @@ Use this My button: 3. Wait for the installation to complete. 4. Depending on your Home Assistant version, you may be prompted for network security keys. - If you are using Z-Wave for the first time, leave all the fields empty and select **Submit**. The system will generate network security keys for you. - - If this Z-Wave dongle has already been paired with secure devices, you need to enter the previously used network key as the S0 network key. S2 security keys will be automatically generated for you. - - Make sure that you keep a backup of these keys in a safe place in case you need to move your Z-Wave dongle to another device. Copy and paste them somewhere safe. + - If this Z-Wave adapter has already been paired with secure devices, you need to enter the previously used network key as the S0 network key. S2 security keys will be automatically generated for you. + - Make sure that you keep a backup of these keys in a safe place in case you need to move your Z-Wave adapter to another device. Copy and paste them somewhere safe. 5. Wait for the Z-Wave JS add-on to start up. -6. Once the installation is complete, the **Device info** of the Z-Wave controller is shown. +6. Once the installation is complete, the **Device info** of the Z-Wave adapter is shown. - You successfully installed the Z-Wave integration and the Z-Wave JS add-on. - You can now [add](/integrations/zwave_js/#adding-a-new-device-to-the-z-wave-network) devices to the Z-Wave network. {% note %} -While your Z-Wave mesh is permanently stored on your dongle, the additional metadata is not. When the Z-Wave integration starts up the first time, it will interview your entire Z-Wave network. Depending on the number of devices paired with the Z-Wave dongle, this can take a while. You can speed up this process by manually waking up your battery-powered devices. Most of the time, this is a button press on those devices (see their manual). It is not necessary to exclude and re-include devices from the mesh. +While your Z-Wave mesh is permanently stored on your adapter, the additional metadata is not. When the Z-Wave integration starts up the first time, it will interview your entire Z-Wave network. Depending on the number of devices paired with the Z-Wave adapter, this can take a while. You can speed up this process by manually waking up your battery-powered devices. Most of the time, this is a button press on those devices (see their manual). It is not necessary to exclude and re-include devices from the mesh. {% endnote %} ### Adding a new device to the Z-Wave network @@ -135,7 +136,7 @@ While your Z-Wave mesh is permanently stored on your dongle, the additional meta 2. Select the Z-Wave integration. - Then, on the entry of the hub, select {% icon "ic:baseline-arrow-forward-ios" %} to open the device info page. 3. Select **Add device**. - - The Z-Wave controller is now in inclusion mode. + - The Z-Wave adapter is now in inclusion mode. 4. Check, if your device supports SmartStart: - On the packaging, check for the SmartStart label. - Find the QR code. It can be on the packaging or on the device itself. @@ -148,55 +149,56 @@ While your Z-Wave mesh is permanently stored on your dongle, the additional meta - Set the device in inclusion mode. Refer to the device manual to see how this is done. - If your device is included using S2 security, you may be prompted to enter a PIN number provided with your device. Often, this PIN is provided with the documentation _and_ is also printed on the device itself. For more information on secure inclusion, refer to [this section](/integrations/zwave_js/#should-i-use-secure-inclusion). 6. The UI should confirm that the device was added. After a short while (seconds to minutes), the entities should also be created. -7. **Troubleshooting**: If the controller fails to add/find your device, cancel the inclusion process. +7. **Troubleshooting**: If the adapter fails to add/find your device, cancel the inclusion process. - In some cases, it might help to first [remove](/integrations/zwave_js/#removing-a-device-from-the-z-wave-network) a device (exclusion) before you add it, even when the device has not been added to this Z-Wave network yet. - Another approach would be to factory reset the device. Refer to the device manual to see how this is done. **Important:** -1. **Do not move your Z-Wave stick to include devices.** Moving the controller is no longer necessary and leads to broken routes. -2. **Do not initiate device inclusion from the Z-Wave stick itself.** This is no longer supported. +1. **Do not move your Z-Wave adapter to include devices.** Moving the adapter is no longer necessary and leads to broken routes. +2. **Do not initiate device inclusion from the Z-Wave adapter itself.** This is no longer supported. ### Removing a device from the Z-Wave network -Do this before using the device with another controller, or when you don't use the device anymore. It removes the device from the Z-Wave network stored on the controller. It also removes the device and all its entities from Home Assistant. You can not join a device to a new network if it is still paired with a controller. +Do this before using the device with another adapter, or when you don't use the device anymore. It removes the device from the Z-Wave network stored on the adapter. It also removes the device and all its entities from Home Assistant. You can not join a device to a new network if it is still paired with an adapter. 1. In Home Assistant, go to {% my integrations title="**Settings** > **Devices & services**" %}. 2. Select the **Z-Wave** integration. - Then, select the cogwheel {% icon "mdi:cog-outline" %}. 3. Select **Remove a device**, then **Start exclusion**. - - The Z-Wave controller is now in exclusion mode. + - The Z-Wave adapter is now in exclusion mode. 4. Put the device you want to remove in exclusion mode. Refer to its manual how this is done. 5. The UI should confirm that the device was removed and the device and entities will be removed from Home Assistant. -## Migrating a Z-Wave network to a new controller +## Migrating a Z-Wave network to a new adapter -Do this if you have an existing Z-Wave network and want to use a new controller. This will reset your current controller (remove all network information from it) and remove the controller from Home Assistant. The Z-Wave integration with all its entities will stay in Home Assistant. The new controller is added to Home Assistant and paired with the existing network. +Do this if you have an existing Z-Wave network and want to use a new adapter. This will reset your current adapter (remove all network information from it) and remove the adapter from Home Assistant. The Z-Wave integration with all its entities will stay in Home Assistant. The new adapter is added to Home Assistant and paired with the existing network. ### Prerequisites - Administrator rights in Home Assistant -- If you want to migrate from a 500 series controller, before starting migration, update the controller to SDK 6.61+ +- If you want to migrate from a 500 series adapter, before starting migration, update the adapter to SDK 6.61+ - Check the documentation of your device to see if and how they can be updated. - [Steps to update Aeotec Z-Stick 5](https://aeotec.freshdesk.com/support/solutions/articles/6000252294-z-stick-gen5-v1-02-firmware-update). -### To migrate a Z-Wave network to a new controller +### To migrate a Z-Wave network to a new adapter 1. In Home Assistant, go to {% my integrations title="**Settings** > **Devices & services**" %}. 2. Select the **Z-Wave** integration. - Then, select the cogwheel {% icon "mdi:cog-outline" %}. -3. Under **Backup and restore**, select **Migrate controller**. -4. Select **Migrate to a new controller**. +3. Under **Backup and restore**, select **Migrate adapter**. +4. Select **Migrate to a new adapter**. + - To confirm device reset, select **Submit**. - - **Info**: This will initiate a backup of the network information and factory reset the controller. All the stored network information will be removed. -5. When the **Unplug your controller** dialog shows up, unplug your old controller. - - Connect the new controller. - - Confirm that you connected the new controller by selecting **Submit**. + - **Info**: This will initiate a backup of the network information and factory reset the adapter. All the stored network information will be removed. +5. When the **Unplug your adapter** dialog shows up, unplug your old adapter. + - Connect the new adapter. + - Confirm that you connected the new adapter by selecting **Submit**. 6. Follow the steps on screen. -## Overriding the radio frequency region of the controller in the Z-Wave JS add-on +## Overriding the radio frequency region of the adapter in the Z-Wave JS add-on -The frequency used by Z-Wave devices depends on your region. For 700 and 800 series controllers, this frequency can be changed. The frequency of end devices cannot, so you need to make sure to buy devices specific to your region. +The frequency used by Z-Wave devices depends on your region. For 700 and 800 series adapters, this frequency can be changed. The frequency of end devices cannot, so you need to make sure to buy devices specific to your region. If you are using the Z-Wave JS add-on, Home Assistant automatically changes the radio frequency region to match the region/country you're in. If needed, you can override this setting. @@ -204,20 +206,20 @@ If you are using the Z-Wave JS add-on, Home Assistant automatically changes the - Administrator rights in Home Assistant - All your Z-Wave devices must be specified for that region -- Note: this procedure only applies if your controller is [set up using the Z-Wave JS add-on](#setting-up-a-z-wave-js-server) +- Note: this procedure only applies if your adapter is [set up using the Z-Wave JS add-on](#setting-up-a-z-wave-js-server) -### To override the radio frequency region of your Z-Wave controller +### To override the radio frequency region of your Z-Wave adapter 1. Go to {% my supervisor_addon addon="core_zwave_js" title="**Settings** > **Add-ons** > **Z-Wave JS**" %}. 2. Open the **Configuration** tab. 3. In the **Options** section, select the **Radio Frequency Region**. 4. To apply your changes, select **Save**. - - Your Z-Wave controller is now ready to communicate with devices that were specified for your chosen region. + - Your Z-Wave adapter is now ready to communicate with devices that were specified for your chosen region. 5. To return to the default setting and use the region defined by Home Assistant, under **Radio Frequency Region** choose **Automatic**. ## Backing up your Z-Wave network -It's recommended to create a backup before making any major changes to your Z-Wave network. For example, before migrating from one controller to another, or before resetting your controller. The backup stores your Z-Wave controller's non-volatile memory (NVM), which contains your network information including paired devices. It is stored in a binary file that you can download. +It's recommended to create a backup before making any major changes to your Z-Wave network. For example, before migrating from one adapter to another, or before resetting your adapter. The backup stores your Z-Wave adapter's non-volatile memory (NVM), which contains your network information including paired devices. It is stored in a binary file that you can download. ### Prerequisites @@ -234,7 +236,7 @@ It's recommended to create a backup before making any major changes to your Z-Wa ## Updating the firmware of your Z-Wave device -Controllers and devices with the Firmware Update Metadata Command Class allow you to update the firmware by uploading a firmware file. In those cases, you can start the firmware update from the device page in Home Assistant. Refer to the documentation of the device manufacturer to find the corresponding firmware file. An example is the [firmware page by Zooz](https://www.support.getzooz.com/kb/article/1158-zooz-ota-firmware-files/). +Adapters and devices with the Firmware Update Metadata Command Class allow you to update the firmware by uploading a firmware file. In those cases, you can start the firmware update from the device page in Home Assistant. Refer to the documentation of the device manufacturer to find the corresponding firmware file. An example is the [firmware page by Zooz](https://www.support.getzooz.com/kb/article/1158-zooz-ota-firmware-files/). {% note %} **Risk of damage to the device due to firmware update** @@ -266,31 +268,33 @@ The Home Assistant and Z-Wave JS teams do not take any responsibility for any da - An interrupted update can damage your device. 5. Select **Begin firmware update** and wait for it to complete. -## Resetting a Z-Wave controller +## Resetting a Z-Wave adapter It is recommended to back up your Z-Wave network before resetting the device. -- The controller will forget all devices it is paired with. +- The adapter will forget all devices it is paired with. - All Z-Wave devices for this network will be removed from Home Assistant. -- If there are any devices still paired with the controller when it is reset, they will have to be removed from their old network before they can be re-paired. + +- If there are any devices still paired with the adapter when it is reset, they will have to go through the exclusion process before they can be re-paired. - The device firmware will remain on the device. ### Prerequisites - Administrator rights on Home Assistant - [Backup your Z-Wave network](#backing-up-your-z-wave-network) -- [Remove all devices that are paired with your controller from the network](#removing-a-device-from-the-z-wave-network). - - Removing can be done by any controller, not just the one that originally managed the network. In theory, this could also be done later. +- [Remove all devices that are paired with your adapter from the network](#removing-a-device-from-the-z-wave-network). + - Removing can be done by any adapter, not just the one that originally managed the network. In theory, this could also be done later. -### To reset a Z-Wave controller +### To reset a Z-Wave adapter 1. In Home Assistant, go to {% my integrations title="**Settings** > **Devices & services**" %}. 2. Select the **Z-Wave** integration. - Then, on the entry of the hub, select {% icon "ic:baseline-arrow-forward-ios" %} to open the device info page. 3. Under **Device info**, select the three dots {% icon "mdi:dots-vertical" %} menu, then select **Factory reset**. - ![Screenshot showing the device panel of a Z-Wave controller](/images/integrations/z-wave/z-wave-controller-commands.png) -4. Once the process is finished, you can use this controller to start a new network, or pass it on to someone else. + + ![Screenshot showing the device panel of a Z-Wave adapter](/images/integrations/z-wave/z-wave-controller-commands.png) +4. Once the process is finished, you can use this adapter to start a new network, or pass it on to someone else. ## Special Z-Wave entities @@ -300,7 +304,7 @@ The Z-Wave integration provides several special entities, some of which are avai 1. **Node status** sensor: This sensor shows the node status for a given Z-Wave device. The sensor is disabled by default. The available node statuses are explained in the [Z-Wave JS documentation](https://zwave-js.github.io/node-zwave-js/#/api/node?id=status). They can be used in state change automations. For example to ping a device when it is dead, or refresh values when it wakes up. 2. **Ping** button: This button can be pressed to ping a device. It is an alternative to the `zwave_js.ping` action. -3. **Controller/node statistics** sensors: Z-Wave JS collects statistics about communications between [nodes](https://zwave-js.github.io/node-zwave-js/#/api/node?id=quotstatistics-updatedquot) and the [controller](https://zwave-js.github.io/node-zwave-js/#/api/controller?id=quotstatistics-updatedquot). The statistics can be used to troubleshoot RF issues in your environment. These statistics are available in the network configuration and device info panels. But they are also available as sensors which are disabled by default. +3. **Adapter/node statistics** sensors: Z-Wave JS collects statistics about communications between [nodes](https://zwave-js.github.io/node-zwave-js/#/api/node?id=quotstatistics-updatedquot) and the [adapter](https://zwave-js.github.io/node-zwave-js/#/api/controller?id=quotstatistics-updatedquot). The statistics can be used to troubleshoot RF issues in your environment. These statistics are available in the network configuration and device info panels. But they are also available as sensors which are disabled by default. ### Conditional entities @@ -320,8 +324,8 @@ The following features can be accessed from the integration configuration panel: - **Add device:** Allows you to pre-provision a SmartStart device or start the inclusion process for adding a new device to your network. - **Remove device:** Starts the exclusion process for removing a device from your network. -- **Rebuild network routes:** Forces your network to rediscover routes to the controller from each device. This is useful when devices or the controller have moved to a new location, or if you are having significant problems with your network, but it also generates a lot of network traffic and should be used sparingly. -- **[Controller statistics](https://zwave-js.github.io/node-zwave-js/#/api/controller?id=quotstatistics-updatedquot):** Provides statistics about communication between the controller and other devices, allowing you to troubleshoot your network's RF quality. +- **Rebuild network routes:** Discovers new routes between the adapter and the device. This is useful when devices or the adapter have moved to a new location, or if you are having significant problems with your network, but it also generates a lot of network traffic and should be used sparingly. +- **[Adapter statistics](https://zwave-js.github.io/node-zwave-js/#/api/controller?id=quotstatistics-updatedquot):** Provides statistics about communication between the adapter and other devices, allowing you to troubleshoot your network's RF quality. - **Third-party data opt-in/out:** Allows you to opt-in or out of telemetry that the Z-Wave JS project collects to help inform development decisions, influence manufacturers, etc. This telemetry is disabled by default and has to be opted in to be activated. ### Integration menu @@ -333,16 +337,16 @@ Some features can be accessed from the menu of integration itself. As they are n #### Network devices -The following features can be accessed from the device panel of any Z-Wave device on your network aside from the controller: +The following features can be accessed from the device panel of any Z-Wave device on your network aside from the adapter: ![Z-Wave device panel](/images/integrations/z-wave/z-wave-device-info.png) - **Configure:** Provides an easy way to look up and update configuration parameters for the device. While there is an existing action for setting configuration parameter values, this UI may sometimes be quicker to use for one-off changes. - **Re-interview:** Forces the device to go through the interview process again so that Z-Wave-JS can discover all of its capabilities. Can be helpful if you don't see all the expected entities for your device. -- **Rebuild routes:** Forces the device to rediscover its optimal route back to the controller. Use this if you think you are experiencing unexpected delays or RF issues with your device. Your device may be less responsive during this process. -- **Remove failed:** Forces the controller to remove the device from the controller. Can be used when a device has failed and it can't go through the normal exclusion process. -- **[Statistics](https://zwave-js.github.io/node-zwave-js/#/api/node?id=quotstatistics-updatedquot):** Provides statistics about communication between this device and the controller, allowing you to troubleshoot RF issues with the device. -- **Update:** Updates a device's firmware using a manually uploaded firmware file. Only some devices support this feature (controllers and devices with the Firmware Update Metadata Command Class). +- **Rebuild routes:** Discovers new routes between the adapter and the device. Use this if you think you are experiencing unexpected delays or RF issues with your device. Your device may be less responsive during this process. +- **Remove failed:** Removes the device from the adapter without excluding the device from the network. Can be used when a device has failed and it can't go through the normal exclusion process. +- **[Statistics](https://zwave-js.github.io/node-zwave-js/#/api/node?id=quotstatistics-updatedquot):** Provides statistics about communication between this device and the adapter, allowing you to troubleshoot RF issues with the device. +- **Update:** Updates a device's firmware using a manually uploaded firmware file. Only some devices support this feature (adapters and devices with the Firmware Update Metadata Command Class). - **Download diagnostics:** Exports a JSON file describing the entities of this specific device. ## Actions @@ -873,7 +877,7 @@ If you are using Home Assistant Container or you don't want to use the built-in ### Running [Z-Wave JS Server](https://github.com/zwave-js/zwave-js-server) -This application provides the connection between your Z-Wave USB stick and Home Assistant. The Home Assistant Z-Wave integration connects to this server via a WebSocket connection. You need to run this Z-Wave JS server before you can use the integration. +This application provides the connection between your Z-Wave adapter and Home Assistant. The Home Assistant Z-Wave integration connects to this server via a WebSocket connection. You need to run this Z-Wave JS server before you can use the integration. There are multiple ways to run this server: The chart below illustrates Options 1 and 2, which are available for Home Assistant OS only. @@ -903,7 +907,7 @@ This method provides the same server application and UI as the Z-Wave JS UI add- This is considered a very advanced use case. In this case you run the Z-Wave JS Server or Z-Wave JS UI NodeJS application directly. Installation and maintaining this is out of scope for this document. See the [Z-Wave JS server](https://github.com/zwave-js/zwave-js-server) or [Z-Wave JS UI](https://github.com/zwave-js/zwave-js-ui/) GitHub repository for information. {% note %} -[Supported Z-Wave dongle](/docs/z-wave/controllers/#supported-z-wave-usb-sticks--hardware-modules). The Z-Wave controller dongle should be connected to the same host as where the Z-Wave JS server is running. In the configuration for the Z-Wave JS server, you need to provide the path to this stick. It's recommended to use the `/dev/serial-by-id/yourdevice` version of the path to your stick, to make sure the path doesn't change over reboots. The most common known path is `/dev/serial/by-id/usb-0658_0200-if00`. +[Supported Z-Wave adapter](/docs/z-wave/controllers/#supported-z-wave-usb-sticks--hardware-modules). The Z-Wave adapter should be connected to the same host as where the Z-Wave JS server is running. In the configuration for the Z-Wave JS server, you need to provide the path to this adapter. It's recommended to use the `/dev/serial-by-id/yourdevice` version of the path to your adapter, to make sure the path doesn't change over reboots. The most common known path is `/dev/serial/by-id/usb-0658_0200-if00`. {% endnote %} {% note %} @@ -934,15 +938,15 @@ You can also keep track of the road map for the Z-Wave integration [here](https: ## FAQ: Installation and configuration -### Which Z-Wave controller should I buy? +### Which Z-Wave adapter should I buy? -Z-Wave supports all known 500-, 700-, and 800-series Z-Wave controllers. If you are just starting out, we recommend that you purchase a 800-series controller (with firmware updated to >=7.23.2). +Z-Wave supports all known 500, 700, and 800 series Z-Wave adapters. If you are just starting out, we recommend that you purchase a 800-series adapter (with firmware updated to >=7.23.2). -For more information, see [Supported Z-Wave dongles](/docs/z-wave/controllers/#supported-z-wave-usb-sticks--hardware-modules) +For more information, see [Supported Z-Wave adapters](/docs/z-wave/controllers/#supported-z-wave-usb-sticks--hardware-modules) ### Why was I (not) automatically prompted to install Z-Wave? -Some Z-Wave USB sticks can be auto-discovered, which can simplify the Z-Wave setup process. The following devices have been tested with discovery, and offer a quick setup experience; however, these are **not** all of the devices supported by Z-Wave: +Some Z-Wave adapters can be auto-discovered, which can simplify the Z-Wave setup process. The following devices have been tested with discovery, and offer a quick setup experience; however, these are **not** all of the devices supported by Z-Wave: | Device | Identifier | Vendor | | -------------------- | ---------- | ---------------------------------------------------------------------------------- | @@ -1014,7 +1018,7 @@ By default, Z-Wave prefers Security S2, if supported. Security S0 is used only w ### Where can I see the security keys in the Z-Wave JS add-on? -After the initial setup of the Z-Wave controller, you can view the security keys in the Z-Wave JS add-on. Go to {% my supervisor_addon addon="core_zwave_js" title="**Settings** > **Add-ons** > **Z-Wave JS**" %} and open the **Configuration** tab. You can now see the three S2 keys and the S0 key. The network security key is a legacy configuration setting, identical to the S0 key. +After the initial setup of the Z-Wave adapter, you can view the security keys in the Z-Wave JS add-on. Go to {% my supervisor_addon addon="core_zwave_js" title="**Settings** > **Add-ons** > **Z-Wave JS**" %} and open the **Configuration** tab. You can now see the three S2 keys and the S0 key. The network security key is a legacy configuration setting, identical to the S0 key. ## FAQ: Troubleshooting topics @@ -1028,9 +1032,9 @@ After ensuring you are using an extension cable, rebuild network routes. The combination of these two steps corrects a large number of reported difficulties. -### I have an Aeotec Gen5 controller, and it isn't detected on my Raspberry Pi 4? +### I have an Aeotec Gen5 adapter, and it isn't detected on my Raspberry Pi 4? -The first-generation Gen5 controller has a known bug when plugged into a Pi 4 and possibly other systems. Aeotec released the Gen5+ stick to correct this bug. Gen5 users can plug their sticks into a USB 2.0 hub in order to overcome the issue. +The first-generation Gen5 adapter has a known bug when plugged into a Pi 4 and possibly other systems. Aeotec released the Gen5+ stick to correct this bug. Gen5 users can plug their adapters into a USB 2.0 hub in order to overcome the issue. ### I do not see any entities created for my device in Home Assistant @@ -1040,7 +1044,7 @@ If you are certain that your device should have entities and you do not see them ### My device doesn't automatically update its status in HA if I control it manually -Your device might not send automatic status updates to the controller. While the best advice would be to update to recent Z-Wave Plus devices, there is a workaround with active polling (request the status). +Your device might not send automatic status updates to the adapter. While the best advice would be to update to recent Z-Wave Plus devices, there is a workaround with active polling (request the status). Z-Wave does not automatically poll devices on a regular basis. Polling can quickly lead to network congestion and should be used very sparingly and only where necessary. @@ -1069,7 +1073,7 @@ When trying to determine why something isn't working as you expect, or when repo ### How do I address interference issues? -Many users have reported issues with interference when the USB stick was directly connected to the machine (proximity). If you are having issues, try to use a short USB 2.0 A (male to female) extension cord. +Many users have reported issues with interference when the adapter was directly connected to the machine (proximity). If you are having issues, try to use a short USB 2.0 A (male to female) extension cord. ### How do I access the Z-Wave logs? @@ -1103,11 +1107,11 @@ Set the log level for `zwave_js_server` to a level higher than `debug`. This can This sections lists functionality that is available in Z-Wave but that is not currently supported in Home Assistant. -### Setting the controller into learn mode to receive network information +### Setting the adapter into learn mode to receive network information In Home Assistant, it is currently not possible to set the Z-Wave controller into learn mode to receive network information from another controller. -### Including / excluding a controller in an existing network using [classic inclusion](#classic-inclusion-versus-smartstart) +### Including / excluding a adapter in an existing network using [classic inclusion](#classic-inclusion-versus-smartstart) A Z-Wave controller that manages an empty network can also join a different network and act as a secondary controller there. However, with Home Assistant, this is not possible. Home Assistant does not allow the Z-Wave controller to join another network, because Home Assistant acts as the central hub. @@ -1115,9 +1119,9 @@ A Z-Wave controller that manages an empty network can also join a different netw In Home Assistant, a single [association group](#association-group) is implemented: -- **Group 1**: This is an association group that includes only one device. It is used after a [factory reset](#controller), to send a **Device Reset Locally Notification**. +- **Group 1**: This is an association group that includes only one device. It is used after a [factory reset](#resetting-a-z-wave-adapter), to send a **Device Reset Locally Notification**. -This association group is used when Home Assistant [resets the Z-Wave controller](#controller). +This association group is used when Home Assistant [resets the Z-Wave adapter](#resetting-a-z-wave-adapter). Under normal circumstances, it is not necessary to add a device to this group. @@ -1174,7 +1178,7 @@ An _association group_ in Z-Wave terminology is a group of devices that another ### SmartStart -SmartStart enabled products can be added into a Z-Wave network by scanning the Z-Wave QR Code present on the product with a controller providing SmartStart inclusion. +SmartStart enabled products can be added into a Z-Wave network by scanning the Z-Wave QR Code present on the product with an adapter supporting SmartStart inclusion. No further action is required and the SmartStart product will be added automatically within 10 minutes of being switched on in the network vicinity. Not all devices support SmartStart. Some devices require [classic inclusion](#classic-inclusion-versus-smartstart). For documentation on adding a device to Home Assistant, refer to [adding a new device to the Z-Wave network](#adding-a-new-device-to-the-z-wave-network). ### Terminology mapping table @@ -1188,8 +1192,8 @@ This removes all paired Z-Wave devices and their entities, the Z-Wave JS add-on, ### To remove Z-Wave JS from Home Assistant 1. [Remove the device from your Z-Wave network](/integrations/zwave_js/#removing-a-device-from-the-z-wave-network). - - Do this for each device that is joined to your network so that it is no longer paired to the controller. - - You cannot add a device to a new controller while it is still paired with an old one. + - Do this for each device that is joined to your network so that it is no longer paired to the adapter. + - You cannot add a device to a new adapter while it is still paired with an old one. - Alternatively, you can factory reset each device. Refer to the device manual to see how this is done. - This usually involves finding the device in your household and pressing a button. 2. Remove the Z-Wave integration. @@ -1201,4 +1205,4 @@ This removes all paired Z-Wave devices and their entities, the Z-Wave JS add-on, - Select **Uninstall**. - Decide whether to also delete the data related to the add-on or whether to keep it. 4. Done. Z-Wave JS is now completely removed from your Home Assistant server. - - You can now use your Z-Wave devices and controller on a new server. + - You can now use your Z-Wave devices and adapter on a new server. From f1b97334d55935bbc598d323ec1be655f9e1e08a Mon Sep 17 00:00:00 2001 From: c0ffeeca7 <38767475+c0ffeeca7@users.noreply.github.com> Date: Thu, 3 Jul 2025 10:42:41 +0200 Subject: [PATCH 011/130] Z-Wave backup: device is no longer reset during backup (#39823) --- source/_integrations/zwave_js.markdown | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/_integrations/zwave_js.markdown b/source/_integrations/zwave_js.markdown index 4c728351cce..6c0fbf3ec2c 100644 --- a/source/_integrations/zwave_js.markdown +++ b/source/_integrations/zwave_js.markdown @@ -190,7 +190,7 @@ Do this if you have an existing Z-Wave network and want to use a new adapter. Th 4. Select **Migrate to a new adapter**. - To confirm device reset, select **Submit**. - - **Info**: This will initiate a backup of the network information and factory reset the adapter. All the stored network information will be removed. + - **Info**: This will initiate a backup of the network information. All the stored network information will be removed. 5. When the **Unplug your adapter** dialog shows up, unplug your old adapter. - Connect the new adapter. - Confirm that you connected the new adapter by selecting **Submit**. From 6a921a895eed4fae8171726d19cfbdcb2817ddc2 Mon Sep 17 00:00:00 2001 From: c0ffeeca7 <38767475+c0ffeeca7@users.noreply.github.com> Date: Thu, 3 Jul 2025 11:19:36 +0200 Subject: [PATCH 012/130] Terminology: standardize spelling of three dots menu (#39825) --- source/_docs/automation/using_blueprints.markdown | 2 +- source/_docs/configuration/troubleshooting.markdown | 2 +- source/_docs/organizing/areas.markdown | 2 +- source/_docs/organizing/categories.markdown | 2 +- source/_docs/tools/dev-tools.markdown | 2 +- source/_includes/common-tasks/beta_version.md | 2 +- .../_includes/integrations/remove_device_service_steps.md | 2 +- source/_integrations/application_credentials.markdown | 2 +- source/_integrations/dlna_dms.markdown | 2 +- source/_integrations/heos.markdown | 4 ++-- source/_integrations/homee.markdown | 2 +- source/_integrations/matter.markdown | 4 ++-- source/_integrations/monzo.markdown | 6 +++--- source/_integrations/ntfy.markdown | 2 +- source/_integrations/onkyo.markdown | 2 +- source/_integrations/reolink.markdown | 4 ++-- source/_integrations/telegram_bot.markdown | 2 +- source/_integrations/xiaomi_ble.markdown | 2 +- source/_integrations/zha.markdown | 2 +- source/_integrations/zwave_js.markdown | 6 +++--- source/getting-started/onboarding_dashboard.markdown | 2 +- source/voice_control/aliases.markdown | 4 ++-- 22 files changed, 30 insertions(+), 30 deletions(-) diff --git a/source/_docs/automation/using_blueprints.markdown b/source/_docs/automation/using_blueprints.markdown index ffa50ecdcb4..ce6834b1262 100644 --- a/source/_docs/automation/using_blueprints.markdown +++ b/source/_docs/automation/using_blueprints.markdown @@ -75,7 +75,7 @@ The quickest way to get these changes, is by re-importing the blueprint. This wi ### To re-import a blueprint 1. Go to **{% my blueprints title="Settings > Automations & Scenes > Blueprints" %}**. -2. On the blueprint that you want to re-import, select the three-dot menu, and select **Re-import blueprint**. +2. On the blueprint that you want to re-import, select the three dots {% icon "mdi:dots-vertical" %} menu, and select **Re-import blueprint**. ## Updating an imported blueprint in YAML diff --git a/source/_docs/configuration/troubleshooting.markdown b/source/_docs/configuration/troubleshooting.markdown index 41107da42e7..9ca1d9be1ee 100644 --- a/source/_docs/configuration/troubleshooting.markdown +++ b/source/_docs/configuration/troubleshooting.markdown @@ -127,7 +127,7 @@ Once you enable debug logging, you ideally need to make the error happen. Run yo ### Download diagnostics -After you download logs, you will also want to download the diagnostics for the integration giving you trouble. If the integration provides diagnostics, it will appear in the three dot menu next to the integration configuration. +After you download logs, you will also want to download the diagnostics for the integration giving you trouble. If the integration provides diagnostics, it will appear in the three dots {% icon "mdi:dots-vertical" %} menu next to the integration configuration.

Example of Download Diagnostics diff --git a/source/_docs/organizing/areas.markdown b/source/_docs/organizing/areas.markdown index e91254d5892..16e9ad03842 100644 --- a/source/_docs/organizing/areas.markdown +++ b/source/_docs/organizing/areas.markdown @@ -93,7 +93,7 @@ Follow these steps to delete an area. It will be removed from all the floors it If you used this area in automations or script as targets, or with voice assistant, these will no longer work. 1. Go to {% my areas title="**Settings** > **Areas, labels & zones**" %} and select the area card. -2. In the top right corner, select the three dot menu. Then, select **Delete**. +2. In the top right corner, select the three dots {% icon "mdi:dots-vertical" %} menu. Then, select **Delete**. ![Delete area](/images/organizing/area_delete.png) diff --git a/source/_docs/organizing/categories.markdown b/source/_docs/organizing/categories.markdown index 3fd569de1ab..305adc8b6fa 100644 --- a/source/_docs/organizing/categories.markdown +++ b/source/_docs/organizing/categories.markdown @@ -52,7 +52,7 @@ To rename or delete a category, follow these steps: 2. In the top left, select the **Filters** button. ![Select the filter button](/images/organizing/filters_01.png) -3. In the list, find the category you want to edit and select the three dot menu next to it. +3. In the list, find the category you want to edit and select the three dots {% icon "mdi:dots-vertical" %} menu next to it. 4. Select **Edit category** or **Delete category**. ![Screenshot showing the edit and delete buttons for categories](/images/organizing/edit-delete-category.png) diff --git a/source/_docs/tools/dev-tools.markdown b/source/_docs/tools/dev-tools.markdown index bc2000d9149..9eb0807d349 100644 --- a/source/_docs/tools/dev-tools.markdown +++ b/source/_docs/tools/dev-tools.markdown @@ -28,7 +28,7 @@ The Developer Tools is meant for **all** (not just for the developers) to quickl The YAML tab provides buttons to trigger a check of configuration files and to reload the configuration. Reloading is needed to apply changes that you've made to the configuration. -It is almost the same as the option under **Settings** > three dot menu (top right) > **Restart Home Assistant** > **Quick reload**. The only difference is that **Quick reload** reloads all the configuration, whereas this YAML tab allows you to only reload one specific configuration at a time. +It is almost the same as the option under **Settings** > three dots {% icon "mdi:dots-vertical" %} menu (top right) > **Restart Home Assistant** > **Quick reload**. The only difference is that **Quick reload** reloads all the configuration, whereas this YAML tab allows you to only reload one specific configuration at a time. ### Reloading the YAML configuration diff --git a/source/_includes/common-tasks/beta_version.md b/source/_includes/common-tasks/beta_version.md index c354235b6ae..20800feada9 100644 --- a/source/_includes/common-tasks/beta_version.md +++ b/source/_includes/common-tasks/beta_version.md @@ -10,7 +10,7 @@ If you would like to test next release before anyone else, you can install the b content: | 1. In Home Assistant, go to {% my updates title="**System** > **Updates**" %}. - 2. In the top-right corner, select the three-dots menu. + 2. In the top-right corner, select the three dots {% icon "mdi:dots-vertical" %} menu. 3. Select **Join beta**. 4. Go to the {% my configuration title="**Configuration**" %} panel. 5. Install the update that is presented to you. diff --git a/source/_includes/integrations/remove_device_service_steps.md b/source/_includes/integrations/remove_device_service_steps.md index 9096191e1d1..60f1a86fe7a 100644 --- a/source/_includes/integrations/remove_device_service_steps.md +++ b/source/_includes/integrations/remove_device_service_steps.md @@ -1,3 +1,3 @@ 1. Go to {% my integrations title="**Settings** > **Devices & services**" %} and select the integration card. 2. From the list of devices, select the integration instance you want to remove. -3. Next to the entry, select the three-dot {% icon "mdi:dots-vertical" %} menu. Then, select **Delete**. +3. Next to the entry, select the three dots {% icon "mdi:dots-vertical" %} menu. Then, select **Delete**. diff --git a/source/_integrations/application_credentials.markdown b/source/_integrations/application_credentials.markdown index b92fcf10807..930f99b7a94 100644 --- a/source/_integrations/application_credentials.markdown +++ b/source/_integrations/application_credentials.markdown @@ -49,6 +49,6 @@ To delete an application credential, for example because you created a new one, ![Devices and services overflow menu](/images/integrations/application_credentials/devices-and-services-menu.png) 2. In the top right corner, select the three dots {% icon "mdi:dots-vertical" %} menu and select **Application credentials**. -3. Select the credential from the list, select the three-dots menu and select **Delete**. +3. Select the credential from the list, select the three dots {% icon "mdi:dots-vertical" %} menu and select **Delete**. ![Application credential list](/images/integrations/application_credentials/application-credential_delete.png) diff --git a/source/_integrations/dlna_dms.markdown b/source/_integrations/dlna_dms.markdown index 1a14af9f903..afdeb278cef 100644 --- a/source/_integrations/dlna_dms.markdown +++ b/source/_integrations/dlna_dms.markdown @@ -19,7 +19,7 @@ The DLNA Digital Media Server integration allows you to browse and play media fr ## Renaming -The name/title of the DMS device is the same as the title of the config entry. It can be changed on the Integrations Configuration page from the three-dot menu. +The name/title of the DMS device is the same as the title of the config entry. It can be changed on the Integrations Configuration page from the three dots {% icon "mdi:dots-vertical" %} menu. ## Media source URIs diff --git a/source/_integrations/heos.markdown b/source/_integrations/heos.markdown index c1dd47478ef..1a08413b9e8 100644 --- a/source/_integrations/heos.markdown +++ b/source/_integrations/heos.markdown @@ -70,7 +70,7 @@ Password: Once setup, the host name or IP address used to access the HEOS System can be changed by reconfiguring the integration. 1. Go to **{% my integrations icon title="Settings > Devices & Services" %}**. -2. Select **Denon HEOS**. Click the three-dot {% icon "mdi:dots-vertical" %} menu and then select **Reconfigure**. +2. Select **Denon HEOS**. Click the three dots {% icon "mdi:dots-vertical" %} menu and then select **Reconfigure**. 3. Enter a new [host name or IP address](/integrations/heos/#host). 4. Click Submit to complete the reconfiguration. @@ -79,7 +79,7 @@ Once setup, the host name or IP address used to access the HEOS System can be ch This integration follows standard integration removal. No extra steps are required. 1. Go to **{% my integrations icon title="Settings > Devices & Services" %}**. -2. Select **Denon HEOS**. Click the three-dot {% icon "mdi:dots-vertical" %} menu and then select **Delete**. +2. Select **Denon HEOS**. Click the three dots {% icon "mdi:dots-vertical" %} menu and then select **Delete**. ## Actions diff --git a/source/_integrations/homee.markdown b/source/_integrations/homee.markdown index 353cc785ef1..a1305c49fb0 100644 --- a/source/_integrations/homee.markdown +++ b/source/_integrations/homee.markdown @@ -100,7 +100,7 @@ This integration supports reconfiguration, allowing you to change the IP address 1. Go to {% my integrations title="**Settings** > **Devices & services**" %} and select the homee integration card. 2. From the list of hubs, select the one you want to reconfigure. -3. Next to the entry, select the three-dot {% icon "mdi:dots-vertical" %} menu. Then, select **Reconfigure**. +3. Next to the entry, select the three dots {% icon "mdi:dots-vertical" %} menu. Then, select **Reconfigure**. ## Removing the integration diff --git a/source/_integrations/matter.markdown b/source/_integrations/matter.markdown index dc99f0c7fe8..d1e0d8007be 100644 --- a/source/_integrations/matter.markdown +++ b/source/_integrations/matter.markdown @@ -313,11 +313,11 @@ Follow these steps if you want to remove a device from a particular Matter contr 1. Go to {% my integrations title="**Settings** > **Devices & services**" %} and on the **Matter** integration card, select **Devices**. 2. From the list of devices, select the device you want to remove from a controller. -3. In the **Device info** section, next to **Share device**, select the three-dot menu. Then, select **Manage fabrics**. +3. In the **Device info** section, next to **Share device**, select the three dots {% icon "mdi:dots-vertical" %} menu. Then, select **Manage fabrics**. 4. From the list, remove the controller of interest. - If you want to remove Apple Home, also remove the Apple Keychain entry. ![image](/images/integrations/matter/matter-remove-from-network.png) -5. If you want to remove the device from Home Assistant itself, select the three-dot menu and select **Delete**. +5. If you want to remove the device from Home Assistant itself, select the three dots {% icon "mdi:dots-vertical" %} menu and select **Delete**. ## About Matter device information diff --git a/source/_integrations/monzo.markdown b/source/_integrations/monzo.markdown index 0690f319f7d..5957fe2e817 100644 --- a/source/_integrations/monzo.markdown +++ b/source/_integrations/monzo.markdown @@ -41,9 +41,9 @@ The **Monzo** {% term integration %} allows you to connect your Monzo bank accou ### Adding a second account 1. To add a second Monzo account in Home Assistant, repeat the above process for creating an OAuth client. -2. Then, in Home Assistant, add the new credentials *before* trying to add the new entry. - - In the top right of **Devices & services** page, select the three dot menu, open **Application Credentials**, and select **Add application credentials** - - It is recommended to include the person's name in the *Name* field so you can distinguish it later. +2. Then, in Home Assistant, add the new credentials *before* trying to add the new entry. + - In the top right of **Devices & services** page, select the three dots {% icon "mdi:dots-vertical" %} menu, open **Application Credentials**, and select **Add application credentials** + - It is recommended to include the person's name in the *Name* field so you can distinguish it later. 3. Once added, you can return to **Devices & services** > **Monzo** > **Add Entry** to proceed with authentication. ## Sensor diff --git a/source/_integrations/ntfy.markdown b/source/_integrations/ntfy.markdown index 2f5ebcb4f9e..e49185ae244 100644 --- a/source/_integrations/ntfy.markdown +++ b/source/_integrations/ntfy.markdown @@ -44,7 +44,7 @@ The ntfy integration can be used to send push notifications from automations and 3. **Adding a topic** - To set up topics for notifications, select the three-dot {% icon "mdi:dots-vertical" %} menu next to the entry of the previously configured ntfy service, then click **{% icon "mdi:plus" %} Add topic**. + To set up topics for notifications, select the three dots {% icon "mdi:dots-vertical" %} menu next to the entry of the previously configured ntfy service, then click **{% icon "mdi:plus" %} Add topic**. You can now choose one of the following options: diff --git a/source/_integrations/onkyo.markdown b/source/_integrations/onkyo.markdown index 7726c370804..146a920d60a 100644 --- a/source/_integrations/onkyo.markdown +++ b/source/_integrations/onkyo.markdown @@ -32,7 +32,7 @@ Listening modes: description: List of listening modes supported by the receiver. {% endconfiguration_basic %} -The above settings can also be adjusted later. To change **Host** or **Volume Resolution**, select the three-dot menu on the integration entry and select **Reconfigure**. +The above settings can also be adjusted later. To change **Host** or **Volume Resolution**, select the three dots {% icon "mdi:dots-vertical" %} menu on the integration entry and select **Reconfigure**. {% include integrations/option_flow.md %} diff --git a/source/_integrations/reolink.markdown b/source/_integrations/reolink.markdown index 72187f76dd2..8c84ac81c04 100644 --- a/source/_integrations/reolink.markdown +++ b/source/_integrations/reolink.markdown @@ -529,7 +529,7 @@ Removing a camera from a NVR/Home Hub can be done by deleting the device followi 3. Go to {% my integrations title="**Settings** > **Devices & services**" %} and select the integration card. 4. From the list of integration entries, select the **x devices** underneath the integration instance of the NVR/Home Hub from which you want to remove a camera. 5. Select the camera you want to remove from the list of devices -6. Underneath the **Device info**, select the three-dot {% icon "mdi:dots-vertical" %} menu. Then, select **Delete**. +6. Underneath the **Device info**, select the three dots {% icon "mdi:dots-vertical" %} menu. Then, select **Delete**. ### Removing a chime @@ -538,7 +538,7 @@ Removing a chime from a doorbell can be done by deleting the chime following the 1. Go to {% my integrations title="**Settings** > **Devices & services**" %} and select the integration card. 2. From the list of integration entries, select the **x devices** underneath the integration instance of the Doorbell/NVR/Home Hub from which you want to remove a chime. 3. Select the chime you want to remove from the list of devices -4. Underneath the **Device info**, select the three-dot {% icon "mdi:dots-vertical" %} menu. Then, select **Delete**. +4. Underneath the **Device info**, select the three dots {% icon "mdi:dots-vertical" %} menu. Then, select **Delete**. This will also decouple the chime from the doorbell in the Reolink app/client. Therefore, the chime will no longer ring when the doorbell is pressed. diff --git a/source/_integrations/telegram_bot.markdown b/source/_integrations/telegram_bot.markdown index 48d5b5accd4..60b9a94ad32 100644 --- a/source/_integrations/telegram_bot.markdown +++ b/source/_integrations/telegram_bot.markdown @@ -107,7 +107,7 @@ To allowlist the chat ID, [retrieve the chat ID](/integrations/telegram#methods- 1. Go to **{% my integrations title="Settings > Devices & services" %}**. 2. Select the Telegram bot integration. -3. Next to the entry, select the three-dot {% icon "mdi:dots-vertical" %} menu. Then, select **Add allowed chat ID**. +3. Next to the entry, select the three dots {% icon "mdi:dots-vertical" %} menu. Then, select **Add allowed chat ID**. {% configuration_basic %} Chat ID: diff --git a/source/_integrations/xiaomi_ble.markdown b/source/_integrations/xiaomi_ble.markdown index 79dc82e2309..ae250a57857 100644 --- a/source/_integrations/xiaomi_ble.markdown +++ b/source/_integrations/xiaomi_ble.markdown @@ -58,7 +58,7 @@ Flower Care firmware update steps: - Press the "+" button on the top right in the devices tab of the app - Add the plant sensor to the app and select an arbitrary plant - Wait for the synchronization of the sensor to finish, and a dialog asking for a firmware update should appear (this might take a few minutes) -- The installed and latest firmware version can be verified by selecting the plant -> three-dot menu -> Hardware settings -> Hardware update +- The installed and latest firmware version can be verified by selecting the plant -> three dots menu -> Hardware settings -> Hardware update - The Flower Care account and app are not required any further for this integration to work Also note that the battery level of the plant sensor can only be retrieved by connecting to the device (reading characteristics), while the other sensor data is broadcasted passively. To prevent battery drainage, a connection is made only once a day. Connecting to the device also requires that the device has a good signal strength. diff --git a/source/_integrations/zha.markdown b/source/_integrations/zha.markdown index 414f23da333..1679564d30d 100644 --- a/source/_integrations/zha.markdown +++ b/source/_integrations/zha.markdown @@ -558,7 +558,7 @@ Prerequisites and steps can vary depending on the device type, manufacturer, and {% endnote %} 1. Navigate to the Zigbee device's configuration page, -2. In the options menu (the "three-dots" icon), select **Manage Zigbee device**, +2. In the options menu (the "three dots" icon), select **Manage Zigbee device**, 3. Select the **Bindings** tab in the pop-up dialog, 4. Choose the device from the dropdown list of _Bindable devices_ (or _Bindable groups_), 5. Confirm the Bind or Unbind action: diff --git a/source/_integrations/zwave_js.markdown b/source/_integrations/zwave_js.markdown index 6c0fbf3ec2c..044b85c8d3d 100644 --- a/source/_integrations/zwave_js.markdown +++ b/source/_integrations/zwave_js.markdown @@ -1082,7 +1082,7 @@ Many users have reported issues with interference when the adapter was directly ##### Enable Z-Wave JS logging 1. Go to the Z-Wave integration panel: {% my integration badge domain="zwave_js" %} -2. In the top-right corner, select the three-dot {% icon "mdi:dots-vertical" %} menu and select **Enable debug logging**. +2. In the top-right corner, select the three dots {% icon "mdi:dots-vertical" %} menu and select **Enable debug logging**. - **Result**: The log level will be set to `debug` for the integration, library, and optionally the driver (if the driver log level is not already set to `verbose`, `debug`, or `silly`), and all Z-Wave JS logs will be added to the Home Assistant logs. 3. If you want to change the log level, on the Z-Wave integration panel: {% my integration badge domain="zwave_js" %}, select the cogwheel {% icon "mdi:cog-outline" %}. - Select the **Logs** tab, then select the log level. @@ -1090,7 +1090,7 @@ Many users have reported issues with interference when the adapter was directly ##### Disable Z-Wave JS logging 1. Go to the Z-Wave integration panel: {% my integration badge domain="zwave_js" %} -2. In the top-right corner, select the three-dot {% icon "mdi:dots-vertical" %} menu and select **Disable debug logging**. +2. In the top-right corner, select the three dots {% icon "mdi:dots-vertical" %} menu and select **Disable debug logging**. - **Result**: The log level will be reset to its previous value for the integration, library, and driver, and the Home Assistant frontend will automatically send you the Z-Wave logs generated during that time period for download. #### The advanced way @@ -1198,7 +1198,7 @@ This removes all paired Z-Wave devices and their entities, the Z-Wave JS add-on, - This usually involves finding the device in your household and pressing a button. 2. Remove the Z-Wave integration. - Go to {% my integrations title="**Settings** > **Devices & services**" %} and select the integration card. - - Next to the integration entry, select the three-dot {% icon "mdi:dots-vertical" %} menu. + - Next to the integration entry, select the three dots {% icon "mdi:dots-vertical" %} menu. - Select **Delete**. 3. If it hasn't been deleted automatically, remove the Z-Wave JS add-on. - Go to {% my supervisor_addon addon="core_zwave_js" title="**Settings** > **Add-ons** > **Z-Wave JS**" %}. diff --git a/source/getting-started/onboarding_dashboard.markdown b/source/getting-started/onboarding_dashboard.markdown index 922ddde4c36..82b703c6649 100644 --- a/source/getting-started/onboarding_dashboard.markdown +++ b/source/getting-started/onboarding_dashboard.markdown @@ -122,7 +122,7 @@ In the following steps, we will create a new dashboard and edit some card settin 12. Now let's delete the other weather card. - In the top right corner, select the pencil. ![Dashboard - edit the dashboard](/images/getting-started/onboarding_edit_dashboard_01.png) - - On the card, select the three-dot menu and select **Delete**. + - On the card, select the three dots {% icon "mdi:dots-vertical" %} menu and select **Delete**. ![Dashboard - delete card](/images/getting-started/onboarding_dashboard_delete_card.png) 13. Finally, we want to move the weather card to the top left corner. - On the bottom of the card, select the number or use the minus button to enter `1`. diff --git a/source/voice_control/aliases.markdown b/source/voice_control/aliases.markdown index 143ecfa26a7..ba2c632467e 100644 --- a/source/voice_control/aliases.markdown +++ b/source/voice_control/aliases.markdown @@ -33,12 +33,12 @@ There are multliple ways to add an alias of an entity: ## Adding an alias of a floor 1. To add an alias for a floor, go to **Settings** > **Areas, labels & zones**. -2. Next to the floor of interest, select the three-dot menu, then select **Edit floor**. +2. Next to the floor of interest, select the three dots {% icon "mdi:dots-vertical" %}, then select **Edit floor**. 3. Select **Add alias** and enter the alias you want to use for that floor. 4. **Save** your changes. -### Area-less aliases for entities with an assigned area +### Area-less aliases for entities with an assigned area It’s good practice to add areas to entity canonical names, such as Living room lamp. However, since Assist can both infer the area and explicitly extract it from sentences, it’s a very good idea to add simplified aliases to all your exposed entities. In this case, having the Lamp alias set for the Living room lamp would allow you to turn on the lamp in the living room or simply turn on the lamp, when asking a satellite in the living room. From 9ba93c2e7f4ce15aa137208f340eb05dceb71681 Mon Sep 17 00:00:00 2001 From: essys Date: Thu, 3 Jul 2025 11:46:30 +0200 Subject: [PATCH 013/130] Update upc_connect.markdown (#39828) --- source/_integrations/upc_connect.markdown | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/_integrations/upc_connect.markdown b/source/_integrations/upc_connect.markdown index bf6d15e4883..546cdf32e1a 100644 --- a/source/_integrations/upc_connect.markdown +++ b/source/_integrations/upc_connect.markdown @@ -18,7 +18,7 @@ related: ha_quality_scale: legacy --- -The `upc_connect` {% term integration %} offers presence detection by looking at connected devices to a [Connect Box](https://www.upc.ch/en/internet/learn-about-internet/) from [Liberty Global](https://www.libertyglobal.com) (also known as UPC Cablecom in Switzerland) which is an Internet provider in Switzerland, Austria, the Netherlands (under Ziggo) and Hungary (under Vodafone). +The `upc_connect` {% term integration %} offers presence detection by looking at connected devices to a [Connect Box](https://www.upc.ch/en/internet/learn-about-internet/) from [Liberty Global](https://www.libertyglobal.com) (also known as UPC Cablecom in Switzerland) which is an Internet provider in Switzerland, Austria, the Netherlands (under Ziggo), Hungary (under Vodafone) and Poland (under PLAY). {% important %} This integration works by logging into the router with a password. The router can only have one active session at any time, so if you want to access your router settings then stop Home Assistant first. From fb8a74a801447f013daa447e932bd1c8e3b8731f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ab=C3=ADlio=20Costa?= Date: Thu, 3 Jul 2025 14:30:24 +0100 Subject: [PATCH 014/130] Add WWHA badge and devices to Nuki Matter (#39729) --- source/_integrations/nuki_matter.markdown | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/source/_integrations/nuki_matter.markdown b/source/_integrations/nuki_matter.markdown index bdd10cda24b..990aee35b9f 100644 --- a/source/_integrations/nuki_matter.markdown +++ b/source/_integrations/nuki_matter.markdown @@ -14,12 +14,16 @@ ha_iot_class: Local Push ha_integration_type: virtual ha_iot_standard: - matter +works_with: + - matter --- -[Nuki](https://nuki.io) is committed to making sure their products are up-to-date and ready to use in Home Assistant. +{% include integrations/wwha.md url="https://nuki.io" name="Nuki" %} -Nuki Matter devices work locally and integrate seamlessly with the Matter integration in Home Assistant. As all connectivity is happening locally, status updates and controlling your devices happen instantly in Home Assistant. +## Supported devices -{% my add_matter_device badge domain=page.ha_domain %} +The following devices are supported: -[Learn more about Matter in Home Assistant.](/integrations/matter/) +- [Nuki Smart Lock Go](https://nuki.io/en-uk/products/smart-lock-go) +- [Nuki Smart Lock Pro](https://nuki.io/en-uk/products/smart-lock-pro-5th-gen) +- [Nuki Smart Lock Ultra](https://nuki.io/en-uk/products/smart-lock-ultra) From 91baa10d0debbaae42d35059df0e80086d483f95 Mon Sep 17 00:00:00 2001 From: Gord <31004434+googanhiem@users.noreply.github.com> Date: Thu, 3 Jul 2025 17:25:40 +0100 Subject: [PATCH 015/130] Upload blog on Nuki joining WWHA (#39830) --- ...i-joins-works-with-home-assistant.markdown | 70 ++++++++++++++++++ source/images/blog/2025-07-nuki/art.jpg | Bin 0 -> 32641 bytes source/images/blog/2025-07-nuki/lock.jpg | Bin 0 -> 47693 bytes 3 files changed, 70 insertions(+) create mode 100644 source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown create mode 100644 source/images/blog/2025-07-nuki/art.jpg create mode 100644 source/images/blog/2025-07-nuki/lock.jpg diff --git a/source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown b/source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown new file mode 100644 index 00000000000..a0d715c0806 --- /dev/null +++ b/source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown @@ -0,0 +1,70 @@ +--- +layout: post +title: "Nuki joins Works with Home Assistant" +description: "Three new lock types are joining, all certified by our team to provide the best experience possible with Home Assistant" +date: 2025-07-03 00:00:01 +date_formatted: "July 3, 2025" +author: Miranda Bishop +comments: true +categories: Works-with-Home-Assistant +og_image: /images/blog/2025-07-nuki/art.jpg +--- + +Nuki Joins Works with Home Assistant + +We're thrilled to welcome [Nuki](https://nuki.io/) to the [Works with Home Assistant](https://works-with.home-assistant.io/) program! Nuki creates some slick-looking smart locks that you can fit to most doors (or even on top of existing locks). They are constantly pioneering new and exciting features, while also using the open standards we support. Nuki is today bringing three different lock types to the program, all certified by our team to provide the best experience possible with Home Assistant. + +## Unlocking their origin + +Nuki started just over 10 years ago, with their first smart lock that was called the 'magic black box'. It was this award-winning design that evolved into the sleek Nuki Smart Locks that are available today. Keeping everything in the family, the brand was started by brothers Martin and Jürgen. Frustrated with the hassle of carrying a door key in their sports kit, the brothers launched a successful Kickstarter and have been innovating ever since. They design their smart locks in Austria and manufacture them in Europe. Their locks are available across Europe, and in early July, they launched the Nuki Smart Lock in the U.S. + +Nuki devices are certified for use with the [Home Assistant Matter integration](/integrations/matter/), which is now [officially certified](/blog/2025/03/10/matter-certification/). Like all 'Works with' certified devices, Nuki locks prioritize local control, so you can manage your day-to-day home security without relying on a cloud connection. + +

+

"Joining the 'Works with Home Assistant' program is a logical step for us. We believe strongly in the power of open ecosystems and giving control to our customers. Home Assistant represents a vibrant community dedicated to innovation and customization, and we are thrilled to align our products with this vision. This integration ensures our customers can build the smart home they want, with the products they trust. The 'Works with Home Assistant' certification provides customers with the confidence that Nuki's products have been tested for compatibility and offer a smooth integration experience."

+- Matthias Kerstner, Head of Product at Nuki. +
+ +## Devices + +

Smart lock proThis lock is turning heads faster than it turns bolts

+ +In case you didn't know, Works with Home Assistant differs from other certification programs as products are rigorously tested in-house to ensure they work seamlessly out of the box. Any company joining also commits to providing long-term support and firmware updates while being a positive force in the Home Assistant community. Works with Home Assistant is operated by the [Open Home Foundation](https://www.openhomefoundation.org/), and the support of [Home Assistant Cloud](/cloud/) subscribers funds this work. + +Our team has been busy testing the Nuki locks for some time and has certified the following Matter-over-Thread enabled devices. It's important to note that to set up the lock, calibrate it, and activate Matter you will need to use the Nuki app. However, there is no hard requirement for a cloud account or account registration in order to use these locks. Once the device is active and connected via Matter, you can manage it purely through Home Assistant, and can even delete the app. + +- [Nuki Smart Lock Go](https://nuki.io/en-uk/products/smart-lock-go) +- [Nuki Smart Lock Pro](https://nuki.io/en-uk/products/smart-lock-pro-5th-gen) +- [Nuki Smart Lock Ultra](https://nuki.io/en-uk/products/smart-lock-ultra) + +## Insane speeds, literally + +The devices certified include two cylindrical models, the Nuki Smart Lock Pro and the Nuki Smart Lock Ultra, which both feature a brushless motor and three speed settings. The speediest of these is called the 'Insane' setting. This ultra-fast setting is ideal for those in a hurry, but you can also pick from 'standard' or 'gentle' to move at a more leisurely pace. The gentle setting is also perfect for quieter unlocking, so you're not disturbing others if you're coming home after a night shift or an early morning jog. + +We love that the cylindrical devices come with a rechargeable battery to reduce e-waste. Each cylindrical lock comes with both white and black band options, so you can match your existing hardware or your home's style. The Nuki Smart Lock Pro can retrofit over a current lock, whereas the Nuki Smart Lock Ultra comes with its own cylinder. + +If you're looking for a solid entry-level choice instead, the Nuki Smart Lock Go is a great option, which uses four AA batteries. Both the Smart Lock Go and Smart Lock Pro can be installed in under five minutes, with no drilling or special tools required, which may mean even if you're renting you could install a smart lock. Works with Home Assistant is all about providing more choice to the community, and Nuki is expanding the smart lock offerings. + +## A keyless future + +All of the models listed work locally, as this is a requirement of the 'Works with' program so that you can ensure you feel safe and secure in your smart home. However, some users may wish to access these devices remotely too, allowing you to unlock the door for guests, contractors, family, or friends. If you're looking for remote access, this can either be provided by the Nuki App, or via your Home Assistant system with something like [Home Assistant Cloud](/cloud/) (which supports the development of Home Assistant but also helps bring more 'Works with' partners to the program 🤝). + +We're really excited to have Nuki join our certified devices, and see the use cases the community will come up with to integrate their smart locks into the rest of their smart home. + +### FAQ ON WORKS WITH HOME ASSISTANT + +***Q: If I have a device that is not listed under 'Works with Home Assistant' does this mean it's not supported?*** + +A: Most Nuki locks will work via Matter with Home Assistant and we have even tried out a couple of older locks with good results. However, we have only officially tested and certified the devices listed above. If there is any other device missing from this list it just means that it hasn't gone through testing with our team or doesn't fit the requirements of the program. It might function well, and may be added to the testing schedule later down the road, or it might work under a different connectivity type that we don't currently test under the program. + +***Q: Ok, so what's the point of the Works with program?*** + +A: It highlights the devices we know work well with Home Assistant and the brands that make a long-term commitment to keeping support for these devices going. We look for brands that will bring their key functionality into Home Assistant, operate locally without the need for cloud logins, and continue to do so long-term. + +***Q: How were these devices tested?*** + +A: All devices in this list were tested using a standard Home Assistant Yellow with the built-in Thread border router and our [certified Matter Integration](/integrations/matter/).  If you have another hub, border router setup, or integration, that's not a problem. We test against these as they are the most effective way for our team to certify within our ecosystem. + +***Q: Will you be adding more Nuki devices to the program?*** + +A: All of the main lock products Nuki currently sells are now represented here in the 'Works with' program. We're thrilled to foster a close relationship with the team at Nuki to work together on any upcoming releases or add in further products that are not yet listed here. diff --git a/source/images/blog/2025-07-nuki/art.jpg b/source/images/blog/2025-07-nuki/art.jpg new file mode 100644 index 0000000000000000000000000000000000000000..b44575aac72171487802e359ded04f14f22431a4 GIT binary patch literal 32641 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 PA*%5HZ^VPyzxDqEO%fuy literal 0 HcmV?d00001 diff --git a/source/images/blog/2025-07-nuki/lock.jpg b/source/images/blog/2025-07-nuki/lock.jpg new file mode 100644 index 0000000000000000000000000000000000000000..1dfe9eebb35e0cd0db5cf20012acd0ad0508c5aa GIT binary patch literal 47693 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 literal 0 HcmV?d00001 From f9652a038f112ba4b3514d1119cd96876a9a48e4 Mon Sep 17 00:00:00 2001 From: c0ffeeca7 <38767475+c0ffeeca7@users.noreply.github.com> Date: Thu, 3 Jul 2025 19:05:34 +0200 Subject: [PATCH 016/130] Z-Wave backup: implement review feedback (#39827) Co-authored-by: Martin Hjelmare --- source/_integrations/zwave_js.markdown | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/source/_integrations/zwave_js.markdown b/source/_integrations/zwave_js.markdown index 044b85c8d3d..09cc229e5e9 100644 --- a/source/_integrations/zwave_js.markdown +++ b/source/_integrations/zwave_js.markdown @@ -172,7 +172,7 @@ Do this before using the device with another adapter, or when you don't use the ## Migrating a Z-Wave network to a new adapter -Do this if you have an existing Z-Wave network and want to use a new adapter. This will reset your current adapter (remove all network information from it) and remove the adapter from Home Assistant. The Z-Wave integration with all its entities will stay in Home Assistant. The new adapter is added to Home Assistant and paired with the existing network. +Do this if you have an existing Z-Wave network and want to replace its adapter with a new adapter. The Z-Wave integration with all its entities will stay in Home Assistant. The new adapter is added to Home Assistant and paired with the existing network. ### Prerequisites @@ -189,8 +189,8 @@ Do this if you have an existing Z-Wave network and want to use a new adapter. Th 3. Under **Backup and restore**, select **Migrate adapter**. 4. Select **Migrate to a new adapter**. - - To confirm device reset, select **Submit**. - - **Info**: This will initiate a backup of the network information. All the stored network information will be removed. + - To confirm, select **Submit**. + - **Info**: This will initiate a backup of the network information. 5. When the **Unplug your adapter** dialog shows up, unplug your old adapter. - Connect the new adapter. - Confirm that you connected the new adapter by selecting **Submit**. From 951ed7e9069f4424ca6e8df6770ef44c13a47db6 Mon Sep 17 00:00:00 2001 From: tronikos Date: Thu, 3 Jul 2025 12:52:46 -0700 Subject: [PATCH 017/130] Add removal-instructions in Google Assistant SDK (#39834) --- source/_integrations/google_assistant_sdk.markdown | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/source/_integrations/google_assistant_sdk.markdown b/source/_integrations/google_assistant_sdk.markdown index 62a1fb1c1be..5c93b5ff3b6 100644 --- a/source/_integrations/google_assistant_sdk.markdown +++ b/source/_integrations/google_assistant_sdk.markdown @@ -246,3 +246,8 @@ Then you can converse with Google Assistant by tapping the Assist icon at the to Or by calling the `conversation.process` action. Note: due to a bug in the Google Assistant API, not all responses contain text, especially for home control commands, like turn on the lights. These will be shown as ``. For those, Google Assistant responds with HTML and Home Assistant integrations are [not allowed](https://github.com/home-assistant/architecture/blob/master/adr/0004-webscraping.md) to parse HTML. + + +## Removing the integration + +{% include integrations/remove_device_service.md %} From a509e116cdcbb2e3d22fa70d9597603718f40f28 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 4 Jul 2025 08:54:08 +0200 Subject: [PATCH 018/130] build(deps-dev): bump textlint from 15.1.0 to 15.1.1 (#39841) Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- package-lock.json | 351 ++++++++++++++++++---------------------------- package.json | 2 +- 2 files changed, 139 insertions(+), 214 deletions(-) diff --git a/package-lock.json b/package-lock.json index 3beb48835c4..b076eaaeff2 100644 --- a/package-lock.json +++ b/package-lock.json @@ -20,7 +20,7 @@ "remark-lint-prohibited-strings": "^4.0.0", "remark-lint-unordered-list-marker-style": "^4.0.1", "remark-stringify": "^11.0.0", - "textlint": "^15.1.0", + "textlint": "^15.1.1", "textlint-filter-rule-allowlist": "^4.0.0", "textlint-filter-rule-comments": "^1.2.2", "textlint-rule-common-misspellings": "^1.0.1", @@ -145,17 +145,17 @@ } }, "node_modules/@modelcontextprotocol/sdk": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.13.0.tgz", - "integrity": "sha512-P5FZsXU0kY881F6Hbk9GhsYx02/KgWK1DYf7/tyE/1lcFKhDYPQR9iYjhQXJn+Sg6hQleMo3DB7h7+p4wgp2Lw==", + "version": "1.15.0", + "resolved": "https://registry.npmjs.org/@modelcontextprotocol/sdk/-/sdk-1.15.0.tgz", + "integrity": "sha512-67hnl/ROKdb03Vuu0YOr+baKTvf1/5YBHBm9KnZdjdAh8hjt4FRCPD5ucwxGB237sBpzlqQsLy1PFu7z/ekZ9Q==", "dev": true, - "license": "MIT", "dependencies": { "ajv": "^6.12.6", "content-type": "^1.0.5", "cors": "^2.8.5", "cross-spawn": "^7.0.5", "eventsource": "^3.0.2", + "eventsource-parser": "^3.0.0", "express": "^5.0.1", "express-rate-limit": "^7.5.0", "pkce-challenge": "^5.0.0", @@ -274,66 +274,66 @@ "license": "MIT" }, "node_modules/@textlint/ast-tester": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-tester/-/ast-tester-15.1.0.tgz", - "integrity": "sha512-/CF1FssZt2lA7kmgT59bcQoM48cF0MiSfpvoChIGvZTRurzeHEVMZN+cmQNHQxCiYi4IRYSCWtnwHhNeIyZVfA==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-tester/-/ast-tester-15.1.1.tgz", + "integrity": "sha512-erRVqr2axwgUOapF3ooZ2KNhs2N3EPd92Lw/mwYO3u68Vte4NHwVuH0nS/Dm829YN8GzpvFuGVxRicR8Jzf6Mw==", "dev": true, "dependencies": { - "@textlint/ast-node-types": "15.1.0", + "@textlint/ast-node-types": "15.1.1", "debug": "^4.4.1" } }, "node_modules/@textlint/ast-tester/node_modules/@textlint/ast-node-types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.0.tgz", - "integrity": "sha512-R7laalVk8drfbHDrbRNRHXibmqQLB+s3mVgb2lWliivNrylX1oviz+vB9TT5SRur6PIEJJ54L4WV3gBlJETB5Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.1.tgz", + "integrity": "sha512-4NtgSdB36MmmcDkof8cPDVPiiKzrEzauomk90gCFmY9iLl1hNQDhYANJEaryoQH/rJvjgPVfTYVFD0puI54QDQ==", "dev": true }, "node_modules/@textlint/ast-traverse": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-traverse/-/ast-traverse-15.1.0.tgz", - "integrity": "sha512-303pqxfT4B6nwN7pwF0Hr+/glI1S0lL8GHgUVjo+U5JSGilmsL4/UXK+dEpkFjrdah3Lne/233/fEbvWPgLnmQ==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-traverse/-/ast-traverse-15.1.1.tgz", + "integrity": "sha512-69Syv32wXR++3B9flheislnKEZ/7rnlz9VYds4v9Dv5QnyTgsN3JhaS/d9lcrq3uFNhB0ivGKFMmAcySI2Wt7Q==", "dev": true, "dependencies": { - "@textlint/ast-node-types": "15.1.0" + "@textlint/ast-node-types": "15.1.1" } }, "node_modules/@textlint/ast-traverse/node_modules/@textlint/ast-node-types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.0.tgz", - "integrity": "sha512-R7laalVk8drfbHDrbRNRHXibmqQLB+s3mVgb2lWliivNrylX1oviz+vB9TT5SRur6PIEJJ54L4WV3gBlJETB5Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.1.tgz", + "integrity": "sha512-4NtgSdB36MmmcDkof8cPDVPiiKzrEzauomk90gCFmY9iLl1hNQDhYANJEaryoQH/rJvjgPVfTYVFD0puI54QDQ==", "dev": true }, "node_modules/@textlint/config-loader": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/config-loader/-/config-loader-15.1.0.tgz", - "integrity": "sha512-QrMNa5Rk4Ji1gDr5UY5jD4+1aOp68kUow0DBy68J43u+w8MtfesU8Gskz4EbGf4l5VRt74Ncnh7HBGMqiSTddQ==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/config-loader/-/config-loader-15.1.1.tgz", + "integrity": "sha512-YE1XfFmC5OWOpXu8N+aiX9l9J6DDknrc8SIk8VD9qIi4kXjOM05V/mMU5mYMxBGnPyYq2qFnoTT4yZsthvPCWA==", "dev": true, "dependencies": { - "@textlint/kernel": "15.1.0", - "@textlint/module-interop": "15.1.0", - "@textlint/resolver": "15.1.0", - "@textlint/types": "15.1.0", - "@textlint/utils": "15.1.0", + "@textlint/kernel": "15.1.1", + "@textlint/module-interop": "15.1.1", + "@textlint/resolver": "15.1.1", + "@textlint/types": "15.1.1", + "@textlint/utils": "15.1.1", "debug": "^4.4.1", "rc-config-loader": "^4.1.3" } }, "node_modules/@textlint/feature-flag": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/feature-flag/-/feature-flag-15.1.0.tgz", - "integrity": "sha512-di4POvizQWGMTfaX8s7Tz3bDNtNT5yn0oox2MVbxBNTzKKD5zMYAfGQWWOiWBulnNPqwpPGtWC3z8OvzjJGHnA==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/feature-flag/-/feature-flag-15.1.1.tgz", + "integrity": "sha512-XHI2X2loRu5qJZyXRMjUCh9e5hE9blE6hJ8WoXcTEa+PX/GycywJQes7aNRDGzYjd8hQXujnZyVIzEM8/8PB6A==", "dev": true }, "node_modules/@textlint/fixer-formatter": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/fixer-formatter/-/fixer-formatter-15.1.0.tgz", - "integrity": "sha512-OOGjMMtB44TcURwz7jo7SqEfUSjXbCdcCNyXT187zPV9IFDstYXET+4NG1CQDON0Xe2TLJlRr5zcuVwjPvWk2A==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/fixer-formatter/-/fixer-formatter-15.1.1.tgz", + "integrity": "sha512-54TUdB9Xb8VpXXnm2TQr5uQ7vpoJnerpRFqRkcXvawjUe4hMnYW6yzgvcLv6XCDyQ7DTvls8BB4wWlYmTeXwxQ==", "dev": true, "dependencies": { - "@textlint/module-interop": "15.1.0", - "@textlint/resolver": "15.1.0", - "@textlint/types": "15.1.0", + "@textlint/module-interop": "15.1.1", + "@textlint/resolver": "15.1.1", + "@textlint/types": "15.1.1", "chalk": "^4.1.2", "debug": "^4.4.1", "diff": "^5.2.0", @@ -349,40 +349,40 @@ "dev": true }, "node_modules/@textlint/kernel": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/kernel/-/kernel-15.1.0.tgz", - "integrity": "sha512-D5yAchuZSqoU+NP3/lLaZBwKkOJe9ga+WMB5Tvhzw+FMLQrUYox4zLHFTHsuI2PdV04qRtLh4zGuHnVQCZZnpw==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/kernel/-/kernel-15.1.1.tgz", + "integrity": "sha512-65JIAzJTV4jhMRiJkULREE9/unFbYzXkWRsnjqfIhJtaVwJFrQ3C8mZkAtXMvIGSALf3VzwCjg6dty6DZCcfKw==", "dev": true, "dependencies": { - "@textlint/ast-node-types": "15.1.0", - "@textlint/ast-tester": "15.1.0", - "@textlint/ast-traverse": "15.1.0", - "@textlint/feature-flag": "15.1.0", - "@textlint/source-code-fixer": "15.1.0", - "@textlint/types": "15.1.0", - "@textlint/utils": "15.1.0", + "@textlint/ast-node-types": "15.1.1", + "@textlint/ast-tester": "15.1.1", + "@textlint/ast-traverse": "15.1.1", + "@textlint/feature-flag": "15.1.1", + "@textlint/source-code-fixer": "15.1.1", + "@textlint/types": "15.1.1", + "@textlint/utils": "15.1.1", "debug": "^4.4.1", "fast-equals": "^4.0.3", "structured-source": "^4.0.0" } }, "node_modules/@textlint/kernel/node_modules/@textlint/ast-node-types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.0.tgz", - "integrity": "sha512-R7laalVk8drfbHDrbRNRHXibmqQLB+s3mVgb2lWliivNrylX1oviz+vB9TT5SRur6PIEJJ54L4WV3gBlJETB5Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.1.tgz", + "integrity": "sha512-4NtgSdB36MmmcDkof8cPDVPiiKzrEzauomk90gCFmY9iLl1hNQDhYANJEaryoQH/rJvjgPVfTYVFD0puI54QDQ==", "dev": true }, "node_modules/@textlint/linter-formatter": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/linter-formatter/-/linter-formatter-15.1.0.tgz", - "integrity": "sha512-5IPC64Q7fBq1VepmjEd2w0MMc4BMlnlfURktuVWDErddCueJ2jord6fcjZBbXi8c8RybRCMQzK21j/NjbGJwVg==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/linter-formatter/-/linter-formatter-15.1.1.tgz", + "integrity": "sha512-KfO/ZL/Mmp1jftaeUbNyPZptuBDvn3ZaDsCgDw7qeY0botVr33ndgAG6TfT4BYz8pwqG+aXPKLS7QkN4yofchQ==", "dev": true, "dependencies": { "@azu/format-text": "^1.0.2", "@azu/style-format": "^1.0.1", - "@textlint/module-interop": "15.1.0", - "@textlint/resolver": "15.1.0", - "@textlint/types": "15.1.0", + "@textlint/module-interop": "15.1.1", + "@textlint/resolver": "15.1.1", + "@textlint/types": "15.1.1", "chalk": "^4.1.2", "debug": "^4.4.1", "js-yaml": "^3.14.1", @@ -395,12 +395,12 @@ } }, "node_modules/@textlint/markdown-to-ast": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/markdown-to-ast/-/markdown-to-ast-15.1.0.tgz", - "integrity": "sha512-BmkMknfh13Cu6OkchU3cOK+cAgrvnHdAWe0uSra9IPm65kchb4qDDNZbIwmy/QGHKQ3olasX6w5qe5OvhzdEmg==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/markdown-to-ast/-/markdown-to-ast-15.1.1.tgz", + "integrity": "sha512-PBBXkrx8r1kN0R2HbPKw1/X4zAcPwS7wkb56wE7ERKmCE3uwk1jwhyHO8fPzHt7zfGS2jPqnSgPfdk2JVYPztA==", "dev": true, "dependencies": { - "@textlint/ast-node-types": "15.1.0", + "@textlint/ast-node-types": "15.1.1", "debug": "^4.4.1", "mdast-util-gfm-autolink-literal": "^0.1.3", "neotraverse": "^0.6.18", @@ -413,9 +413,9 @@ } }, "node_modules/@textlint/markdown-to-ast/node_modules/@textlint/ast-node-types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.0.tgz", - "integrity": "sha512-R7laalVk8drfbHDrbRNRHXibmqQLB+s3mVgb2lWliivNrylX1oviz+vB9TT5SRur6PIEJJ54L4WV3gBlJETB5Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.1.tgz", + "integrity": "sha512-4NtgSdB36MmmcDkof8cPDVPiiKzrEzauomk90gCFmY9iLl1hNQDhYANJEaryoQH/rJvjgPVfTYVFD0puI54QDQ==", "dev": true }, "node_modules/@textlint/markdown-to-ast/node_modules/bail": { @@ -645,9 +645,9 @@ } }, "node_modules/@textlint/module-interop": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/module-interop/-/module-interop-15.1.0.tgz", - "integrity": "sha512-qdGmYW/IYEUhOvuQj+KoPM33l8oSp60ltUZTiAXm0Jy1dU1DxO/H8XuM/6PwrI1SZ7D5L6e4M0a/9oRDNjwHvA==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/module-interop/-/module-interop-15.1.1.tgz", + "integrity": "sha512-J+djF/OPkhdHEe2cAWYTmMGxgmbkamlF6g4TyklgZqz9SW0bsuJbSuMGHdIa2uQ8oyXdG9fBUVNd5cWZX8wtxw==", "dev": true }, "node_modules/@textlint/regexp-string-matcher": { @@ -674,75 +674,75 @@ } }, "node_modules/@textlint/resolver": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/resolver/-/resolver-15.1.0.tgz", - "integrity": "sha512-JRLC8QFNRVg/xyd8ckOB3ymkD837+5P8Aq2NWxWjlqdlTqKyMLxgNh6GkJzI/mOOr7dVkH8wzC6EsBgk7XRY8Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/resolver/-/resolver-15.1.1.tgz", + "integrity": "sha512-W7wWaOGzDTfhnSdwYszAOo1VppbXI1f2IbqFWj2cQ2qQ394C7B+Se4AzO5h6ViJWj6h5rToY0k8sxMRYo0RreA==", "dev": true }, "node_modules/@textlint/source-code-fixer": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/source-code-fixer/-/source-code-fixer-15.1.0.tgz", - "integrity": "sha512-UMuo2y7I96OOO1gxXcSvOfH81BuWUG7VN6BLdSfUCrW9960dbjREMdZwD5tq91VkobEZwfgFOcWGghhXOHunLw==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/source-code-fixer/-/source-code-fixer-15.1.1.tgz", + "integrity": "sha512-4Z2/SdUquT60+3skCCQ4CwfNaWELMAr9arCAJxh3tADz0FJwPBuRsMfpb7Nue+rqbdK+iT8SBEadgnksFsY3KA==", "dev": true, "dependencies": { - "@textlint/types": "15.1.0", + "@textlint/types": "15.1.1", "debug": "^4.4.1" } }, "node_modules/@textlint/text-to-ast": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/text-to-ast/-/text-to-ast-15.1.0.tgz", - "integrity": "sha512-P0KW0f+7iZDN1bR2eYjvrhOIe85ksOwMn76hbgiE6ur8A7ApUOShmEFgABKUOpdzXQcYW8fU+2ocdC7np5oPEw==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/text-to-ast/-/text-to-ast-15.1.1.tgz", + "integrity": "sha512-e6FT42OFCV2wivRXFE1TM+wWJEKLjMhuP/PBhWHhoQP4QbF+7jHM/dn9LK6GnaKDbG/TuhZk2d+N5X7YgOHfXQ==", "dev": true, "dependencies": { - "@textlint/ast-node-types": "15.1.0" + "@textlint/ast-node-types": "15.1.1" } }, "node_modules/@textlint/text-to-ast/node_modules/@textlint/ast-node-types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.0.tgz", - "integrity": "sha512-R7laalVk8drfbHDrbRNRHXibmqQLB+s3mVgb2lWliivNrylX1oviz+vB9TT5SRur6PIEJJ54L4WV3gBlJETB5Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.1.tgz", + "integrity": "sha512-4NtgSdB36MmmcDkof8cPDVPiiKzrEzauomk90gCFmY9iLl1hNQDhYANJEaryoQH/rJvjgPVfTYVFD0puI54QDQ==", "dev": true }, "node_modules/@textlint/textlint-plugin-markdown": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/textlint-plugin-markdown/-/textlint-plugin-markdown-15.1.0.tgz", - "integrity": "sha512-n5oqSZNTSs6lTI7G2GGXWNqxI9y1RWv6WKa1llFUJQ+2AX0NK0ERjjRRfXxrgxhH7sHD6cn6CSP/+UUQPsTzFg==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/textlint-plugin-markdown/-/textlint-plugin-markdown-15.1.1.tgz", + "integrity": "sha512-pt7dA1yCcr2xdZumyMFkQ5kY4MrtV9dW1nbriCXPZfDbsZjLj+mpXM+nzOsrFe7YlBLXqI/tZQXfgjiB1/5W7g==", "dev": true, "dependencies": { - "@textlint/markdown-to-ast": "15.1.0", - "@textlint/types": "15.1.0" + "@textlint/markdown-to-ast": "15.1.1", + "@textlint/types": "15.1.1" } }, "node_modules/@textlint/textlint-plugin-text": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/textlint-plugin-text/-/textlint-plugin-text-15.1.0.tgz", - "integrity": "sha512-dAwDUTREjIERhr+zw0WiEymcqlCVzSnKGhsXDDmaE+QIdjheOz5WqVP5A6PKh6lFRjU6rTv8GVDuFecrZXibkQ==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/textlint-plugin-text/-/textlint-plugin-text-15.1.1.tgz", + "integrity": "sha512-tRn18zlWXrjS1c52k0DurOJvr3qwajwQr2vkyisoX6X/HFK+Bf4V0T3McMh+cItSci+EloBO5mwAu4S1eS70/g==", "dev": true, "dependencies": { - "@textlint/text-to-ast": "15.1.0", - "@textlint/types": "15.1.0" + "@textlint/text-to-ast": "15.1.1", + "@textlint/types": "15.1.1" } }, "node_modules/@textlint/types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/types/-/types-15.1.0.tgz", - "integrity": "sha512-cRCGwb0DoCn4UPTDnmYJhAlRNKDKln3lOkwRNphNiDrV9ToD9IBTbkFz9maVK21xKo0HfsMkvoPk6bRGm7NQNQ==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/types/-/types-15.1.1.tgz", + "integrity": "sha512-UUxZxIt3hNWrN84kqn2yEjD4Cgt+aWa7NSBQOueOrh7QHSCJ3banvYiAw8P+rHhRQgLUl6nxZUmETmQVzIIRAQ==", "dev": true, "dependencies": { - "@textlint/ast-node-types": "15.1.0" + "@textlint/ast-node-types": "15.1.1" } }, "node_modules/@textlint/types/node_modules/@textlint/ast-node-types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.0.tgz", - "integrity": "sha512-R7laalVk8drfbHDrbRNRHXibmqQLB+s3mVgb2lWliivNrylX1oviz+vB9TT5SRur6PIEJJ54L4WV3gBlJETB5Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.1.tgz", + "integrity": "sha512-4NtgSdB36MmmcDkof8cPDVPiiKzrEzauomk90gCFmY9iLl1hNQDhYANJEaryoQH/rJvjgPVfTYVFD0puI54QDQ==", "dev": true }, "node_modules/@textlint/utils": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/utils/-/utils-15.1.0.tgz", - "integrity": "sha512-gSmMshUh9y+M3w5IgndFQq8D1wWVkM6Id+lAnJCCcVXMTGEYGMMCTVsM9TVJ+usBET6s1EjJRl0JQjFTfwNPuw==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/utils/-/utils-15.1.1.tgz", + "integrity": "sha512-SAK+ZvVOIDbh+FpaKi4Ma8Rkv6XI2sW8VFtB6dGsxZ+ZEbo6QToWHNlrJ/pmTOfGmRB+yYwyzuWdqW7HIbJfRA==", "dev": true }, "node_modules/@types/concat-stream": { @@ -859,7 +859,6 @@ "resolved": "https://registry.npmjs.org/accepts/-/accepts-2.0.0.tgz", "integrity": "sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==", "dev": true, - "license": "MIT", "dependencies": { "mime-types": "^3.0.0", "negotiator": "^1.0.0" @@ -873,7 +872,6 @@ "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, - "license": "MIT", "dependencies": { "fast-deep-equal": "^3.1.1", "fast-json-stable-stringify": "^2.0.0", @@ -1000,7 +998,6 @@ "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-2.2.0.tgz", "integrity": "sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==", "dev": true, - "license": "MIT", "dependencies": { "bytes": "^3.1.2", "content-type": "^1.0.5", @@ -1070,7 +1067,6 @@ "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -1091,7 +1087,6 @@ "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz", "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==", "dev": true, - "license": "MIT", "dependencies": { "es-errors": "^1.3.0", "function-bind": "^1.1.2" @@ -1105,7 +1100,6 @@ "resolved": "https://registry.npmjs.org/call-bound/-/call-bound-1.0.4.tgz", "integrity": "sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==", "dev": true, - "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.2", "get-intrinsic": "^1.3.0" @@ -1304,7 +1298,6 @@ "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-1.0.0.tgz", "integrity": "sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==", "dev": true, - "license": "MIT", "dependencies": { "safe-buffer": "5.2.1" }, @@ -1317,7 +1310,6 @@ "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.6" } @@ -1327,7 +1319,6 @@ "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.7.2.tgz", "integrity": "sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.6" } @@ -1337,7 +1328,6 @@ "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.2.2.tgz", "integrity": "sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==", "dev": true, - "license": "MIT", "engines": { "node": ">=6.6.0" } @@ -1347,7 +1337,6 @@ "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", "dev": true, - "license": "MIT", "dependencies": { "object-assign": "^4", "vary": "^1" @@ -1436,7 +1425,6 @@ "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -1477,7 +1465,6 @@ "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz", "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==", "dev": true, - "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.1", "es-errors": "^1.3.0", @@ -1497,8 +1484,7 @@ "version": "1.1.1", "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==", - "dev": true, - "license": "MIT" + "dev": true }, "node_modules/emoji-regex": { "version": "8.0.0", @@ -1511,7 +1497,6 @@ "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-2.0.0.tgz", "integrity": "sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -1530,7 +1515,6 @@ "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz", "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.4" } @@ -1540,7 +1524,6 @@ "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.4" } @@ -1550,7 +1533,6 @@ "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz", "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==", "dev": true, - "license": "MIT", "dependencies": { "es-errors": "^1.3.0" }, @@ -1562,8 +1544,7 @@ "version": "1.0.3", "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==", - "dev": true, - "license": "MIT" + "dev": true }, "node_modules/escape-string-regexp": { "version": "4.0.0", @@ -1595,7 +1576,6 @@ "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.6" } @@ -1605,7 +1585,6 @@ "resolved": "https://registry.npmjs.org/eventsource/-/eventsource-3.0.7.tgz", "integrity": "sha512-CRT1WTyuQoD771GW56XEZFQ/ZoSfWid1alKGDYMmkt2yl8UXrVR4pspqWNEcqKvVIzg6PAltWjxcSSPrboA4iA==", "dev": true, - "license": "MIT", "dependencies": { "eventsource-parser": "^3.0.1" }, @@ -1614,13 +1593,12 @@ } }, "node_modules/eventsource-parser": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.2.tgz", - "integrity": "sha512-6RxOBZ/cYgd8usLwsEl+EC09Au/9BcmCKYF2/xbml6DNczf7nv0MQb+7BA2F+li6//I+28VNlQR37XfQtcAJuA==", + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/eventsource-parser/-/eventsource-parser-3.0.3.tgz", + "integrity": "sha512-nVpZkTMM9rF6AQ9gPJpFsNAMt48wIzB5TQgiTLdHiuO8XEDhUgZEhqKlZWXbIzo9VmJ/HvysHqEaVeD5v9TPvA==", "dev": true, - "license": "MIT", "engines": { - "node": ">=18.0.0" + "node": ">=20.0.0" } }, "node_modules/execall": { @@ -1640,7 +1618,6 @@ "resolved": "https://registry.npmjs.org/express/-/express-5.1.0.tgz", "integrity": "sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==", "dev": true, - "license": "MIT", "dependencies": { "accepts": "^2.0.0", "body-parser": "^2.2.0", @@ -1683,7 +1660,6 @@ "resolved": "https://registry.npmjs.org/express-rate-limit/-/express-rate-limit-7.5.1.tgz", "integrity": "sha512-7iN8iPMDzOMHPUYllBEsQdWVB6fPDMPqwjBaFrgr4Jgr/+okjvzAy+UHlYYL/Vs0OsOrMkwS6PJDkFlJwoxUnw==", "dev": true, - "license": "MIT", "engines": { "node": ">= 16" }, @@ -1717,8 +1693,7 @@ "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", - "dev": true, - "license": "MIT" + "dev": true }, "node_modules/fast-equals": { "version": "4.0.3", @@ -1730,8 +1705,7 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", - "dev": true, - "license": "MIT" + "dev": true }, "node_modules/fast-levenshtein": { "version": "2.0.6", @@ -1796,7 +1770,6 @@ "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-2.1.0.tgz", "integrity": "sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==", "dev": true, - "license": "MIT", "dependencies": { "debug": "^4.4.0", "encodeurl": "^2.0.0", @@ -1871,7 +1844,6 @@ "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.6" } @@ -1881,7 +1853,6 @@ "resolved": "https://registry.npmjs.org/fresh/-/fresh-2.0.0.tgz", "integrity": "sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -1915,7 +1886,6 @@ "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz", "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==", "dev": true, - "license": "MIT", "dependencies": { "call-bind-apply-helpers": "^1.0.2", "es-define-property": "^1.0.1", @@ -1940,7 +1910,6 @@ "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz", "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==", "dev": true, - "license": "MIT", "dependencies": { "dunder-proto": "^1.0.1", "es-object-atoms": "^1.0.0" @@ -1966,7 +1935,6 @@ "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz", "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.4" }, @@ -1988,7 +1956,6 @@ "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz", "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.4" }, @@ -2034,7 +2001,6 @@ "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", "dev": true, - "license": "MIT", "dependencies": { "depd": "2.0.0", "inherits": "2.0.4", @@ -2051,7 +2017,6 @@ "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -2061,7 +2026,6 @@ "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", "dev": true, - "license": "MIT", "dependencies": { "safer-buffer": ">= 2.1.2 < 3.0.0" }, @@ -2142,7 +2106,6 @@ "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.10" } @@ -2337,8 +2300,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-4.0.0.tgz", "integrity": "sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==", - "dev": true, - "license": "MIT" + "dev": true }, "node_modules/is-regexp": { "version": "2.1.0", @@ -2415,8 +2377,7 @@ "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "dev": true, - "license": "MIT" + "dev": true }, "node_modules/json5": { "version": "2.2.3", @@ -2564,7 +2525,6 @@ "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz", "integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.4" } @@ -3471,7 +3431,6 @@ "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-1.1.0.tgz", "integrity": "sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -3481,7 +3440,6 @@ "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-2.0.0.tgz", "integrity": "sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==", "dev": true, - "license": "MIT", "engines": { "node": ">=18" }, @@ -4165,7 +4123,6 @@ "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.54.0.tgz", "integrity": "sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.6" } @@ -4175,7 +4132,6 @@ "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-3.0.1.tgz", "integrity": "sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==", "dev": true, - "license": "MIT", "dependencies": { "mime-db": "^1.54.0" }, @@ -4230,7 +4186,6 @@ "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-1.0.0.tgz", "integrity": "sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.6" } @@ -4297,7 +4252,6 @@ "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", "dev": true, - "license": "MIT", "engines": { "node": ">=0.10.0" } @@ -4307,7 +4261,6 @@ "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.4.tgz", "integrity": "sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.4" }, @@ -4320,7 +4273,6 @@ "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", "dev": true, - "license": "MIT", "dependencies": { "ee-first": "1.1.1" }, @@ -4333,7 +4285,6 @@ "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==", "dev": true, - "license": "ISC", "dependencies": { "wrappy": "1" } @@ -4426,7 +4377,6 @@ "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -4467,7 +4417,6 @@ "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-8.2.0.tgz", "integrity": "sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==", "dev": true, - "license": "MIT", "engines": { "node": ">=16" } @@ -4496,7 +4445,6 @@ "resolved": "https://registry.npmjs.org/pkce-challenge/-/pkce-challenge-5.0.0.tgz", "integrity": "sha512-ueGLflrrnvwB3xuo/uGob5pd5FN7l0MsLf0Z87o/UQmRtwjvfylfc9MurIxRAWywCYTgrvpXBcqjV4OfCYGCIQ==", "dev": true, - "license": "MIT", "engines": { "node": ">=16.20.0" } @@ -4531,7 +4479,6 @@ "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", "dev": true, - "license": "MIT", "dependencies": { "forwarded": "0.2.0", "ipaddr.js": "1.9.1" @@ -4545,7 +4492,6 @@ "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", "dev": true, - "license": "MIT", "engines": { "node": ">=6" } @@ -4555,7 +4501,6 @@ "resolved": "https://registry.npmjs.org/qs/-/qs-6.14.0.tgz", "integrity": "sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==", "dev": true, - "license": "BSD-3-Clause", "dependencies": { "side-channel": "^1.1.0" }, @@ -4581,7 +4526,6 @@ "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.6" } @@ -4591,7 +4535,6 @@ "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-3.0.0.tgz", "integrity": "sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==", "dev": true, - "license": "MIT", "dependencies": { "bytes": "3.1.2", "http-errors": "2.0.0", @@ -6297,7 +6240,6 @@ "resolved": "https://registry.npmjs.org/router/-/router-2.2.0.tgz", "integrity": "sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==", "dev": true, - "license": "MIT", "dependencies": { "debug": "^4.4.0", "depd": "^2.0.0", @@ -6342,8 +6284,7 @@ "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "dev": true, - "license": "MIT" + "dev": true }, "node_modules/semver": { "version": "7.7.2", @@ -6363,7 +6304,6 @@ "resolved": "https://registry.npmjs.org/send/-/send-1.2.0.tgz", "integrity": "sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==", "dev": true, - "license": "MIT", "dependencies": { "debug": "^4.3.5", "encodeurl": "^2.0.0", @@ -6386,7 +6326,6 @@ "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-2.2.0.tgz", "integrity": "sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==", "dev": true, - "license": "MIT", "dependencies": { "encodeurl": "^2.0.0", "escape-html": "^1.0.3", @@ -6401,8 +6340,7 @@ "version": "1.2.0", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", - "dev": true, - "license": "ISC" + "dev": true }, "node_modules/shebang-command": { "version": "2.0.0", @@ -6430,7 +6368,6 @@ "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.1.0.tgz", "integrity": "sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==", "dev": true, - "license": "MIT", "dependencies": { "es-errors": "^1.3.0", "object-inspect": "^1.13.3", @@ -6450,7 +6387,6 @@ "resolved": "https://registry.npmjs.org/side-channel-list/-/side-channel-list-1.0.0.tgz", "integrity": "sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==", "dev": true, - "license": "MIT", "dependencies": { "es-errors": "^1.3.0", "object-inspect": "^1.13.3" @@ -6467,7 +6403,6 @@ "resolved": "https://registry.npmjs.org/side-channel-map/-/side-channel-map-1.0.1.tgz", "integrity": "sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==", "dev": true, - "license": "MIT", "dependencies": { "call-bound": "^1.0.2", "es-errors": "^1.3.0", @@ -6486,7 +6421,6 @@ "resolved": "https://registry.npmjs.org/side-channel-weakmap/-/side-channel-weakmap-1.0.2.tgz", "integrity": "sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==", "dev": true, - "license": "MIT", "dependencies": { "call-bound": "^1.0.2", "es-errors": "^1.3.0", @@ -6587,7 +6521,6 @@ "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.2.tgz", "integrity": "sha512-DvEy55V3DB7uknRo+4iOGT5fP1slR8wQohVdknigZPMpMstaKJQWhwiYBACJE3Ul2pTnATihhBYnRhZQHGBiRw==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -6758,25 +6691,25 @@ "dev": true }, "node_modules/textlint": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/textlint/-/textlint-15.1.0.tgz", - "integrity": "sha512-dwWHX5FyqRkF9wt6sG7ACjFZWkBWyRie/u6qEMa8j2afu+SKfIX3Xiy/fE6WyBrT6S3HuRbfPpcLik/PTKDWQA==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/textlint/-/textlint-15.1.1.tgz", + "integrity": "sha512-Agc4dVjwTFZn4EFvUP4o6SUnIxxzaVqgiV73658+ePP06Pr2EoD+WzG+LiMcz8vMg8Dfwuztxbt4fPeVkz2vkQ==", "dev": true, "dependencies": { - "@modelcontextprotocol/sdk": "^1.13.0", - "@textlint/ast-node-types": "15.1.0", - "@textlint/ast-traverse": "15.1.0", - "@textlint/config-loader": "15.1.0", - "@textlint/feature-flag": "15.1.0", - "@textlint/fixer-formatter": "15.1.0", - "@textlint/kernel": "15.1.0", - "@textlint/linter-formatter": "15.1.0", - "@textlint/module-interop": "15.1.0", - "@textlint/resolver": "15.1.0", - "@textlint/textlint-plugin-markdown": "15.1.0", - "@textlint/textlint-plugin-text": "15.1.0", - "@textlint/types": "15.1.0", - "@textlint/utils": "15.1.0", + "@modelcontextprotocol/sdk": "^1.13.1", + "@textlint/ast-node-types": "15.1.1", + "@textlint/ast-traverse": "15.1.1", + "@textlint/config-loader": "15.1.1", + "@textlint/feature-flag": "15.1.1", + "@textlint/fixer-formatter": "15.1.1", + "@textlint/kernel": "15.1.1", + "@textlint/linter-formatter": "15.1.1", + "@textlint/module-interop": "15.1.1", + "@textlint/resolver": "15.1.1", + "@textlint/textlint-plugin-markdown": "15.1.1", + "@textlint/textlint-plugin-text": "15.1.1", + "@textlint/types": "15.1.1", + "@textlint/utils": "15.1.1", "debug": "^4.4.1", "file-entry-cache": "^10.1.1", "glob": "^10.4.5", @@ -6916,9 +6849,9 @@ } }, "node_modules/textlint/node_modules/@textlint/ast-node-types": { - "version": "15.1.0", - "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.0.tgz", - "integrity": "sha512-R7laalVk8drfbHDrbRNRHXibmqQLB+s3mVgb2lWliivNrylX1oviz+vB9TT5SRur6PIEJJ54L4WV3gBlJETB5Q==", + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/@textlint/ast-node-types/-/ast-node-types-15.1.1.tgz", + "integrity": "sha512-4NtgSdB36MmmcDkof8cPDVPiiKzrEzauomk90gCFmY9iLl1hNQDhYANJEaryoQH/rJvjgPVfTYVFD0puI54QDQ==", "dev": true }, "node_modules/textlint/node_modules/brace-expansion": { @@ -7012,7 +6945,6 @@ "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", "dev": true, - "license": "MIT", "engines": { "node": ">=0.6" } @@ -7057,7 +6989,6 @@ "resolved": "https://registry.npmjs.org/type-is/-/type-is-2.0.1.tgz", "integrity": "sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==", "dev": true, - "license": "MIT", "dependencies": { "content-type": "^1.0.5", "media-typer": "^1.1.0", @@ -7628,7 +7559,6 @@ "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -7638,7 +7568,6 @@ "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", "dev": true, - "license": "BSD-2-Clause", "dependencies": { "punycode": "^2.1.0" } @@ -7665,7 +7594,6 @@ "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", "dev": true, - "license": "MIT", "engines": { "node": ">= 0.8" } @@ -8171,8 +8099,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", "integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==", - "dev": true, - "license": "ISC" + "dev": true }, "node_modules/yaml": { "version": "2.3.2", @@ -8184,21 +8111,19 @@ } }, "node_modules/zod": { - "version": "3.25.67", - "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.67.tgz", - "integrity": "sha512-idA2YXwpCdqUSKRCACDE6ItZD9TZzy3OZMtpfLoh6oPR47lipysRrJfjzMqFxQ3uJuUPyUeWe1r9vLH33xO/Qw==", + "version": "3.25.72", + "resolved": "https://registry.npmjs.org/zod/-/zod-3.25.72.tgz", + "integrity": "sha512-Cl+fe4dNL4XumOBNBsr0lHfA80PQiZXHI4xEMTEr8gt6aGz92t3lBA32e71j9+JeF/VAYvdfBnuwJs+BMx/BrA==", "dev": true, - "license": "MIT", "funding": { "url": "https://github.com/sponsors/colinhacks" } }, "node_modules/zod-to-json-schema": { - "version": "3.24.5", - "resolved": "https://registry.npmjs.org/zod-to-json-schema/-/zod-to-json-schema-3.24.5.tgz", - "integrity": "sha512-/AuWwMP+YqiPbsJx5D6TfgRTc4kTLjsh5SOcd4bLsfUg2RcEXrFMJl1DGgdHy2aCfsIA/cr/1JM0xcB2GZji8g==", + "version": "3.24.6", + "resolved": "https://registry.npmjs.org/zod-to-json-schema/-/zod-to-json-schema-3.24.6.tgz", + "integrity": "sha512-h/z3PKvcTcTetyjl1fkj79MHNEjm+HpD6NXheWjzOekY7kV+lwDYnHw+ivHkijnCSMz1yJaWBD9vu/Fcmk+vEg==", "dev": true, - "license": "ISC", "peerDependencies": { "zod": "^3.24.1" } diff --git a/package.json b/package.json index 33d7dd824bb..87cc30524f2 100644 --- a/package.json +++ b/package.json @@ -15,7 +15,7 @@ "remark-lint-prohibited-strings": "^4.0.0", "remark-lint-unordered-list-marker-style": "^4.0.1", "remark-stringify": "^11.0.0", - "textlint": "^15.1.0", + "textlint": "^15.1.1", "textlint-filter-rule-allowlist": "^4.0.0", "textlint-filter-rule-comments": "^1.2.2", "textlint-rule-common-misspellings": "^1.0.1", From 2530ab34d6d1200351558b330ca529c620e1e329 Mon Sep 17 00:00:00 2001 From: Gord <31004434+googanhiem@users.noreply.github.com> Date: Fri, 4 Jul 2025 10:07:53 +0100 Subject: [PATCH 019/130] Fix unclear wording in Nuki blog (#39843) --- .../2025-07-03-nuki-joins-works-with-home-assistant.markdown | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown b/source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown index a0d715c0806..5e1f9bb44e9 100644 --- a/source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown +++ b/source/_posts/2025-07-03-nuki-joins-works-with-home-assistant.markdown @@ -67,4 +67,4 @@ A: All devices in this list were tested using a standard Home Assistant Yellow w ***Q: Will you be adding more Nuki devices to the program?*** -A: All of the main lock products Nuki currently sells are now represented here in the 'Works with' program. We're thrilled to foster a close relationship with the team at Nuki to work together on any upcoming releases or add in further products that are not yet listed here. +A: All of the locks Nuki currently sells are now represented here in the 'Works with' program. We're thrilled to foster a close relationship with the team at Nuki to work together on any upcoming releases or add in further products that are not yet listed here. From 88dc3caf8a7f5d00f999d6871201ae1605bcbc3b Mon Sep 17 00:00:00 2001 From: tronikos Date: Fri, 4 Jul 2025 02:08:16 -0700 Subject: [PATCH 020/130] Add removal-instructions in Opower (#39838) Co-authored-by: c0ffeeca7 <38767475+c0ffeeca7@users.noreply.github.com> --- source/_integrations/opower.markdown | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/source/_integrations/opower.markdown b/source/_integrations/opower.markdown index 3f2a9779b7d..fb34295f4dc 100644 --- a/source/_integrations/opower.markdown +++ b/source/_integrations/opower.markdown @@ -170,3 +170,10 @@ With the above changes your (**{% my config_energy title="Settings > Dashboards - Before opening an issue, ensure you can access the energy usage section/dashboard on your utility website and verify that the data is up-to-date there. - In your energy dashboard in Home Assistant, make sure you use the statistics and not the sensors. + +## Removing the integration + +{% include integrations/remove_device_service.md %} + +If you remove the integration, the statistics are not automatically deleted. +You can find and delete the statistics in {% my developer_statistics title="**Developer Tools** > **Statistics**"%} and search for "opower". From c000b402d45d836ad914077d2d7ff224a6643855 Mon Sep 17 00:00:00 2001 From: tronikos Date: Fri, 4 Jul 2025 02:08:44 -0700 Subject: [PATCH 021/130] Add removal-instructions in Google Generative AI (#39840) --- .../_integrations/google_generative_ai_conversation.markdown | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/source/_integrations/google_generative_ai_conversation.markdown b/source/_integrations/google_generative_ai_conversation.markdown index ec7f6e634b0..cf3a75ad72e 100644 --- a/source/_integrations/google_generative_ai_conversation.markdown +++ b/source/_integrations/google_generative_ai_conversation.markdown @@ -241,3 +241,7 @@ logger: homeassistant.components.conversation.chat_log: debug homeassistant.components.google_generative_ai_conversation: debug ``` + +## Removing the integration + +{% include integrations/remove_device_service.md %} From 18f7cdf726b4fd184908ade596508eabf00626c3 Mon Sep 17 00:00:00 2001 From: Darren Griffin Date: Fri, 4 Jul 2025 14:50:01 +0100 Subject: [PATCH 022/130] Update voice language picker (#39775) Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com> --- .gitignore | 1 + Rakefile | 11 + .../voice-pe/local-cloud/ha-instance.svg | 4 + source/images/voice-pe/local-cloud/house.svg | 10 +- source/voice-pe/index.html | 328 ++++---- source/voice-pe/rounded-path.svg | 3 + source/voice-pe/script.js | 184 ++--- source/voice-pe/styles.css | 729 ++++++++++-------- 8 files changed, 645 insertions(+), 625 deletions(-) create mode 100644 source/images/voice-pe/local-cloud/ha-instance.svg create mode 100644 source/voice-pe/rounded-path.svg diff --git a/.gitignore b/.gitignore index 8ea7efa5afb..878022feb08 100644 --- a/.gitignore +++ b/.gitignore @@ -8,6 +8,7 @@ source/_data/analytics_data.json source/_data/blueprint_exchange_data.json source/_data/version_data.json source/_data/alerts_data.json +source/_data/language_scores.json source/_stash source/stylesheets/screen.css source/.jekyll-cache/ diff --git a/Rakefile b/Rakefile index fbfc5959bd4..333be912563 100644 --- a/Rakefile +++ b/Rakefile @@ -113,3 +113,14 @@ task :version_data do file.write(JSON.generate(remote_data)) end end + +desc "Download supported language data from ohf-voice.github.io" +task :language_scores_data do + uri = URI('https://ohf-voice.github.io/intents/language_scores.json') + + remote_data = JSON.parse(Net::HTTP.get(uri)) + + File.open("#{source_dir}/_data/language_scores.json", "w") do |file| + file.write(JSON.generate(remote_data)) + end +end diff --git a/source/images/voice-pe/local-cloud/ha-instance.svg b/source/images/voice-pe/local-cloud/ha-instance.svg new file mode 100644 index 00000000000..4f9318a15b8 --- /dev/null +++ b/source/images/voice-pe/local-cloud/ha-instance.svg @@ -0,0 +1,4 @@ + + + + diff --git a/source/images/voice-pe/local-cloud/house.svg b/source/images/voice-pe/local-cloud/house.svg index e3f47d124a1..05e9c629d9a 100644 --- a/source/images/voice-pe/local-cloud/house.svg +++ b/source/images/voice-pe/local-cloud/house.svg @@ -1,3 +1,9 @@ - - + + + + + + + + diff --git a/source/voice-pe/index.html b/source/voice-pe/index.html index 8f8e9ebd249..d79da41e375 100644 --- a/source/voice-pe/index.html +++ b/source/voice-pe/index.html @@ -27,7 +27,8 @@ frontpage_image: /images/frontpage/voice-pe-frontpage.jpg Features Specs FAQ - Docs + Docs Buy now
@@ -40,7 +41,8 @@ frontpage_image: /images/frontpage/voice-pe-frontpage.jpg Features Specs FAQ - Docs + Docs Buy now
@@ -217,7 +219,8 @@ frontpage_image: /images/frontpage/voice-pe-frontpage.jpg alt="Front view of the Voice Preview Edition showing the speaker holes">
Buy now - * Recommended MSRP. Prices differ between regions due to varying local market costs and conditions, and subject to individual retailers. + * Recommended MSRP. Prices differ between regions due to varying local market costs and conditions, + and subject to individual retailers.
@@ -461,9 +464,8 @@ frontpage_image: /images/frontpage/voice-pe-frontpage.jpg
-
Bringing
choice to
voice
-
If you have powerful hardware, run voice fully locally, or offload speech processing to - our privacy-first cloud for speedy performance.
+
Bringing choice
to voice
+
Run voice fully locally, or offload speech processing to our privacy-first cloud.
@@ -473,25 +475,61 @@ frontpage_image: /images/frontpage/voice-pe-frontpage.jpg
-
-
-
-
- Local -

Your voice never leaves your home and the processing is pretty accurate, but is hardware-intensive.

+ +
+
+
+
+
+
+ Focused local processing +

Limited to a set list of common home control phrases, this allows even low-powered hardware + system to process speech locally and offline.

+
+ + + + +
+
+
+ Full local processing +

Full speech processing is done locally, requiring high processing power for adequate speed and + accuracy.

+
+ + + + +
+
+
+
+
+ Generic outline drawing of the Voice Preview Edition +
+
+
+ Generic outline drawing of the Voice Preview Edition +
+
-
-
-
-
-
- Cloud -

Your voice is processed on a private cloud, allowing Assist to run fast and very accurately on low-powered hardware.

+
+
+
+
+ Home Assistant Cloud +

Your voice is processed privately on Home Assistant Cloud, allowing Assist to run very accurately + on low-powered hardware.

+
+
-
+