[2026-09-14] eagle: family/how-to/t610-access.md family/plans/t610-addons-deployment.md

This commit is contained in:
Alexey Martemyanov
2026-09-14 12:20:28 +06:00
parent 87381ed135
commit 9c4887a0fe
2 changed files with 126 additions and 21 deletions
+11 -4
View File
@@ -4,9 +4,13 @@
> План переноса: [[family/plans/home-automation-migration-t610]]
> Развёртывание сервисов: [[family/plans/t610-addons-deployment]]
> ✅ **Состояние на 2026-09-14 (Этап 3 почти закрыт, z2m = 16 устройств):** z2m, mbusd (порт 502), modbus-bridge (MQTT + HA-опрос) — развёрнуты аддонами и **работают**. В HA добавлена **MQTT-интеграция**. **HA-конфиг перенесён с TrueNAS** (`.storage` реестры + конфиги + `www/`): HA запущен, **248 сущностей, 11 зон, MQTT-интеграция цела, ошибок нет**. `modbus.host` → `127.0.0.1`. Zigbee-розетка `0xa4c138eb6fbe9d19` (NEO NAS-WR01B, греющий кабель) добавлена, мёртвое `Mini Smart Switch 1` (`0xcc86ecfffe1347fd`) **удалено из z2m**. **Остался последний шаг Этапа 3** — прописать `friendly_name` в z2m (таблица готова, см. [[family/plans/t610-addons-deployment]] §«КРИТИЧЕСКОЕ ОТКРЫТИЕ»), чтобы убрать hex-топики.
> ✅ **Состояние на 2026-09-14 (Этап 3 ЗАКРЫТ, z2m = 14 устройств):** z2m, mbusd (порт 502), modbus-bridge (MQTT + HA-опрос) — развёрнуты аддонами и **работают**. В HA добавлена **MQTT-интеграция**. **HA-конфиг перенесён с TrueNAS** (`.storage` реестры + конфиги + `www/`): HA запущен, **11 зон, MQTT-интеграция цела, ошибок нет**. Zigbee-розетка `0xa4c138eb6fbe9d19` (NEO NAS-WR01B, греющий кабель) добавлена, мёртвые устройства (3 шт.) **удалены из z2m**.
> ✅ **Автоматизации: 16 шт., 15 `on` + 1 `off`, 0 `unavailable`** (было 13 «мёртвых» — `device_id` перемаплены + hex-`entity_id` почищен).
> ✅ **HTTP-варнинг устранён** (блок `http:` → `.storage/http`), **`modbus.host` = `192.168.2.176`** (НЕ `127.0.0.1` — см. питфолл ниже), **modbus-bridge 404 исправлены** (+rebuild аддона).
> ⏸️ **ОСТАЛСЯ ОДИН БЛОКЕР — аппаратный:** 32 заслонки вентиляции `unavailable` (шина не отвечает, exception 0x0B) → CH340 #2 нужно физически подключить к линиям A/B шины. Конфиг верный.
>
> 🔑 **Ключевой вывод:** HA связывает сущности по **`unique_id`**, а не по `entity_id`. Смена `friendly_name` в z2m **сохраняет человеческие `entity_id`** — дублей нет, автоматизации не ломаются. Прежнее опасение снято.
> 🔑 **Ключевой вывод:** HA связывает сущности по **`unique_id`**, а не по `entity_id`. Смена `friendly_name` в z2m **сохраняет человеческие `entity_id`** — дублей нет, автоматизации не ломаются.
> 🔑 **`device_id` НЕ переносится между инстансами HA** — автоматизации, ссылающиеся на `device_id`, надо перемапить по `identifiers`. Подробно: [[family/plans/t610-addons-deployment]] §«ПИТФОЛЛ: device_id ломаются при переносе реестра».
## Основное
@@ -262,9 +266,9 @@ ZONT (modbus-bridge): /dev/serial/by-path/pci-0000:00:12.0-usb-0:3:1.0-por
| Mosquitto broker | `core_mosquitto` | 7.1.1 | ✅ started | 1883 (MQTT), 1884 (WS) |
| Node-RED | `a0d7b954_nodered` | 22.0.6 | ✅ started | 1880 |
| File editor | `core_configurator` | — | ✅ started | web UI |
| **Zigbee2MQTT** | `45df7312_zigbee2mqtt` | 2.14.1-1 | ✅ **started (16 устройств)** | ingress 8099 |
| **Zigbee2MQTT** | `45df7312_zigbee2mqtt` | 2.14.1-1 | ✅ **started (14 устройств)** | ingress 8099 |
| **mbusd** | `local_mbusd` | 1.0.0 | ✅ **started** | 502 (Modbus TCP) |
| **modbus-bridge** | `local_modbus-bridge` | 1.0.0 | ✅ **started — MQTT + HA-опрос** | sniffer шины ZONT |
| **modbus-bridge** | `local_modbus-bridge` | 1.1.0 | ✅ **started — MQTT + HA-опрос** | sniffer шины ZONT |
| Samba share | `core_samba` | — | ⏸️ stopped (нужен пароль) | — |
Репозитории аддонов: официальный + **Zigbee2MQTT** (`https://github.com/zigbee2mqtt/hassio-zigbee2mqtt`) + Local apps.
@@ -304,6 +308,9 @@ ha apps uninstall local_<slug> && ha store reload && ha apps install local_<slug
5. **Сборка идёт через `docker buildx` на хосте**, тянет базовый образ из интернета, занимает несколько минут.
6. **`uart: true`** в манифесте обязателен для доступа к `/dev/serial/by-path/…` (иначе аддон не увидит CH340/Zigbee). Для modbus-bridge дополнительно `host_network: true`.
7. В HA UI local add-ons требуют **Advanced Mode** в профиле (Settings → Apps).
8. **⚠️ Правка файлов аддона (`data/*.tmpl`, `*.py`) НЕ применяется без rebuild.** `run.sh` генерирует runtime-конфиг из копии **внутри образа** (`Dockerfile`: `COPY data/config.template.tmpl /app/config.template.yml`). После правки исходников обязателен **`ha addons rebuild local_modbus-bridge`** — иначе работает старая версия из образа и правки «не видно». Симптом ошибки: `ha addons rebuild <slug>` (команда долгая, ~1 мин).
> 📌 Из SSH-аддона `/addons/` **виден** (это `/addons/modbus-bridge`, без префикса `local_`); изначально казалось, что нет — проверять именно `/addons/<имя-папки>`.
> 📌 `<slug>` в URL аддона = `local_<имя папки>`. Опции из UI кладутся в `/data/options.json` внутри контейнера — читать через `jq`.
+115 -17
View File
@@ -16,9 +16,13 @@ related:
---
# t610 — развёртывание через HA-аддоны
> **Статус (2026-09-14): Этап 1 ✅. Этап 2 ✅ ПОЛНОСТЬЮ. Этап 3 ✅ ОСНОВНОЕ ВЫПОЛНЕНО — реестры и конфиг перенесены, БД с нуля, `localtuya`/HACS сняты, z2m приведён к **14 живым** устройствам (удалены 3 мёртвых), все `entity_id` в HA переименованы в человеческие (**hex = 0**), `friendly_name` в z2m — латиница snake_case, `switch_as_x` восстановлены (виртуальные `light.*` работают), дашборд поправлен.**
> ⚠️ **ОСТАЛОСЬ ПОЧИНИТЬ (блокер): 13 из 16 автоматизаций `unavailable`.** Причина установлена полностью — **две поломки одного класса** (обе от переноса между инстансами): ① `device_id` (9 шт., 20 вхождений) — маппинг собран **9/9**, файл-кандидат готов; ② hex-`entity_id` в `automations.yaml` (2 шт.). См. §«ПИТФОЛЛ: device_id ломаются при переносе реестра». Далее: `sensor.*_summary` template-ошибки (`default(0)`), Этап 4.
> Сервисы: z2m (14), mbusd (502), modbus-bridge (MQTT + HA-опрос), MQTT-интеграция в HA.
> **Статус (2026-09-14, поздняя сессия): Этап 1 ✅. Этап 2 ✅ ПОЛНОСТЬЮ. Этап 3 ✅ ЗАКРЫТ.**
> **Автоматизации: 13/16 `unavailable` → 0 (15 `on` + 1 `off`).** Причины были две, обе устранены: ① `device_id` (9 шт., 20 вхождений) перемаплены по `identifiers`; ② hex-`entity_id` в `automations.yaml` (`light.0xa4c13882a4b42db0` → `light.bed_dimmer`; `switch.0xa4c13873b5c1575b` оказался **артефактом regex** — в файле уже `_l1`/`_l2`). Файл залит, HA перезапущен.
> **HTTP-варнинг устранён:** блок `http:` удалён из `configuration.yaml`, настройки перенесены в `.storage/http` (UI → Network).
> **modbus.host исправлен: `127.0.0.1` → `192.168.2.176`** (mbusd в отдельном контейнере — `127.0.0.1` изнутри HA его не видел).
> **modbus-bridge: HTTP 404 → 200.** Опрашивал HA по hex-`entity_id`; правился `modbus_ha_bridge.py` + `data/config.template.tmpl` + **обязательный rebuild аддона**.
> ⚠️ **ЕДИНСТВЕННЫЙ ОСТАВШИЙСЯ БЛОКЕР (физика, не конфиг): 32 заслонки вентиляции `unavailable`.** mbusd работает (TCP отвечает), но шина **не отвечает** — exception **0x0B** (GATEWAY TARGET DEVICE FAILED TO RESPOND). Вывод: **CH340 #2 воткнут в USB, но линии A/B вентиляционной шины к нему не подключены / шина обесточена.** За Alex.
> Сервисы: z2m (14 устройств), mbusd (502), modbus-bridge (MQTT + HA-опрос), MQTT-интеграция в HA.
> Родительский план: [[family/plans/home-automation-migration-t610]] (Шаг 3 в нём заменяется на этот документ).
> Доступ к хосту, CLI и питфоллы: [[family/how-to/t610-access]].
@@ -336,7 +340,7 @@ curl -s -X POST -H "Authorization: Bearer $T" -H "Content-Type: application/json
**Финал решений Alex:** БД — с нуля; реестры — замена; `localtuya`/HACS/`tuya_local` — НЕ переносим; `Mini Smart Switch 1`**удалён из z2m** (мёртвое: `lastSeen` 2026-01-26, нигде не используется, `unavailable`).
**Staged-комплект:** `~/tmp-t610/stage3/out/`
- конфиги: `configuration.yaml` (правки: `modbus.host``127.0.0.1`; убрана строка `localtuya: debug`), `automations.yaml`, `scripts.yaml`, `scenes.yaml`, `secrets.yaml`
- конфиги: `configuration.yaml` (правки: `modbus.host``127.0.0.1` на момент залива, **позже исправлено на `192.168.2.176`**; убрана строка `localtuya: debug`; **блок `http:` удалён** 2026-09-14 — настройки уехали в `.storage/http`), `automations.yaml`, `scripts.yaml`, `scenes.yaml`, `secrets.yaml`
- `.storage/`: `core.entity_registry`, `core.device_registry`, `core.area_registry`, `core.floor_registry`, `core.restore_state`, `lovelace.home_plan`, `lovelace_dashboards`, `lovelace_resources`, `person`, `zone`, `core.logger`, `homeassistant.exposed_entities`
- `www/`: `card-mod.js`, `floorplan/floor1_ha.svg`, `floorplan/floor2_ha.svg`
@@ -553,7 +557,7 @@ timeout 10 mosquitto_sub -h core-mosquitto -p 1883 -u zont -P "$MPW" \
⚠️ **Питфолл:** при переносе реестров **`core.config_entries` тоже нужен**, если есть виртуальные сущности (`switch_as_x`, `template`, helper'ы) — иначе их entry теряются и сущности висят `unavailable`. Мы не переносили его ради сохранения MQTT-интеграции → добавляли `switch_as_x` точечно.
#### 🔴 ПИТФОЛЛ: `device_id` ломаются при переносе реестра — ✅ МАППИНГ СОБРАН 9/9, ЗАЛИВКА НЕ ВЫПОЛНЕНА
#### 🔴 ПИТФОЛЛ: `device_id` ломаются при переносе реестра — ✅ ЗАКРЫТО 2026-09-14
**Симптом:** после переноса реестров и старта HA **13 из 16 автоматизаций стали `unavailable`**. В `ha core logs`:
```
@@ -600,11 +604,94 @@ jq -r '.data.devices[] | select((.identifiers|tostring)|contains("<ieee_без_0
**Мораль:** при переносе HA надо чистить **и `device_id`, и hex-`entity_id`** одновременно — иначе автоматизация «чинится» наполовину.
##### План починки (собран, НЕ залит)
##### План починки — ВЫПОЛНЕН 2026-09-14 (автоматизации 0 `unavailable`)
**Файл-кандидат:** `~/tmp-t610/etap3-fix/automations.fixed.yaml` — 20 замен `device_id`, 0 старых осталось, все 20 новых проверены по реестру t610 (`core.device_registry`), все ссылки валидны. Бэкап: `automations.yaml.bak-20260914-114235`.
**Файл:** `~/tmp-t610/etap3-fix/automations.fixed.yaml` — 20 замен `device_id`, 0 старых осталось, все 20 новых проверены по реестру t610. Бэкап на t610: `/config/automations.yaml.bak-devid-20260914-124733`.
**Порядок:** доделать hex-`entity_id` (`light.0xa4c13882a4b42db0``light.bed_dimmer`; решить по `switch.0xa4c13873b5c1575b`) → `ha core stop` → залить `automations.yaml``ha core start` → проверить, что автоматизации `on`.
**Уточнение про `switch.0xa4c13873b5c1575b` (закрыт вопрос l1/l2):** это был **артефакт regex**, а не реальная ссылка. В `automations.yaml` уже стояли правильные `switch.0xa4c13873b5c1575b_l1` (авт. `office_pass_switch_table`) и `switch.0xa4c13873b5c1575b_l2` (авт. `office_pass_switch_main`). Проверка `grep -E 'switch\.0xa4c13873b5c1575b(?!_l)'`**0 совпадений**. Чинить нечего.
**Реально исправленный hex-`entity_id` — только один:** `light.0xa4c13882a4b42db0``light.bed_dimmer` (2 вхождения, автоматизация «Dimmer bed cycle»: и в `state_attr()`, и в `target.entity_id`).
**Порядок (выполнен):** `ha core stop`-эквивалент через `ha core restart` → залив `automations.yaml` → проверка API.
**Результат (факт, 2026-09-14):** `automation.*`**16 сущностей: 15 `on` + 1 `off` (0 `unavailable`)**. Единственная `off``automation.ventilation_automation_on`: это **нормальное состояние** (вентиляция управляется через modbus-шину, а не по расписанию), идентично TrueNAS.
**Важный побочный вывод:** 12 `entity_id` внутри device-действий формата `entity_id: <32-hex>` — это **реестровые `id` сущностей**, а НЕ строки `domain.name`. Они **совпали** и менять их не пришлось, потому что при переименовании реестра через jq мы меняли только поле `entity_id`, а `id` оставался нетронутым (перенесён с TrueNAS). Проверено: 12/12 найдены в `core.entity_registry`.
##### 🔴 ТРЕТЬЯ ПОЛОМКА ТОГО ЖЕ КЛАССА: hex-`entity_id` зашиты в код local add-on (modbus-bridge)
**Симптом:** modbus-bridge бесконечно логирует `HA poll: sensor.0xa4c13862d39377e6_temperature HTTP 404`.
**Причина:** hex-`entity_id` (`sensor.0xa4c13862d39377e6_temperature`, `switch.0xa4c138f8da8bc478`) зашиты **в код аддона**, а не в опции:
- `/addons/modbus-bridge/modbus_ha_bridge.py` (строки 74, 82, 89 — встроенный дефолт `DEFAULT_CONFIG`)
- `/addons/modbus-bridge/data/config.template.tmpl` (строки 112, 125)
Правильные значения: `sensor.office_temperature_sensor_temperature`, `switch.recirculation_pump`.
**⚠️ ГЛАВНЫЙ ПИТФОЛЛ: правки в `data/*.tmpl` НЕ применяются без rebuild.** `run.sh` генерирует runtime `/app/config.yml` из **`/app/config.template.yml`** — копии внутри **образа** (`Dockerfile`: `COPY data/config.template.tmpl /app/config.template.yml`). Поэтому после правки исходников обязателен **`ha addons rebuild local_modbus-bridge`** (без него работает старая версия из образа — я на этом попался).
**Проверка после rebuild:** в логе `HA poll -> sensor.office_temperature_sensor_temperature = 23.96` (200, без 404).
#### 🔧 ПИТФОЛЛ: `http:` в `configuration.yaml` игнорируется после миграции
**Симптом (варнинг в HA):** `YAML configuration is ignored after migration` / `The HTTP configuration in configuration.yaml has already been migrated and is now being ignored... This stops working in version 2027.2.0.` → надо удалить блок `http:` и управлять через **Settings → System → Network**.
**Что было:** в `configuration.yaml` блок
```yaml
http:
use_x_forwarded_for: true
trusted_proxies:
- 172.16.0.0/12
```
Но в `.storage/http` этих ключей **НЕ было** → простое удаление блока **потеряло бы доверие к Caddy-прокси** (HA отдаёт 400 на запросы через прокси — критично для Этапа 4).
**Правильный фикс (выполнен):**
1. Бэкап `configuration.yaml``.bak-http-<ts>`; бэкап `.storage/http``.bak-<ts>`.
2. Добавить в `.storage/http``data.stable` (jq, локально): `use_x_forwarded_for: true`, `trusted_proxies: ["172.16.0.0/12"]`. Файл положить **при остановленном HA** (`ha core stop`), иначе HA перезапишет.
3. Удалить блок `http:` из `configuration.yaml`, оставить комментарий-пояснение.
4. `ha core start` → HA сам выставляет `data.yaml_migration_done: true`.
**Проверка:** `jq '.data.stable | {server_port, use_x_forwarded_for, trusted_proxies}' /config/.storage/http` → порт 80, настройки на месте; `curl -o /dev/null -w '%{http_code}' http://192.168.2.176/` → 200.
> 📌 **Общий принцип (для любых настроек, мигрированных в UI):** прежде чем удалять YAML-блок, **сверить**, что все его ключи реально есть в `.storage/<domain>`. Иначе настройка молча теряется.
#### 🔴 ПИТФОЛЛ (КРИТИЧНЫЙ): `modbus.host` не может быть `127.0.0.1` — mbusd в отдельном контейнере
**Симптом:** 32 `switch.*_damper` (заслонки вентиляции) `unavailable`, **0 живых modbus-сенсоров**, хотя `local_mbusd` = `started` и порт 502 на хосте открыт.
**Причина:** в `configuration.yaml` было `modbus.host: 127.0.0.1`. HA Core сидит **в своём контейнере** (`172.30.32.1`), а `local_mbusd` — в **другом контейнере**, пробросивший порт на **хост**. Для HA `127.0.0.1` = он сам → таймаут.
**Фикс:** `host: 192.168.2.176` (IP хоста t610, порт 502 проброшен Docker'ом). Проверка: `nc -z 192.168.2.176 502` → OK.
> ⚠️ **Не путать:** в логе mbusd `conn_open(): accepting connection from 172.30.32.1` + мгновенный `conn_close()` = признак неверного адреса. Успешное подключение выглядит как **`conn_open(): accepting connection from 192.168.2.176`** и **БЕЗ последующего `conn_close`** (HA держит коннект).
#### 📡 ПИТФОЛЛ: диагностика modbus-шины через прямой TCP-запрос
Проверка «жива ли шина», не залезая в HA (скрипт `~/tmp-t610/etap3-fix/mbtest.sh`):
```bash
# Modbus TCP: FC=03, UnitID=0b(11), Start=0000, Qty=0001
printf '\x00\x01\x00\x00\x00\x06\x0b\x03\x00\x00\x00\x01' > /tmp/mbreq.bin
nc -w 5 192.168.2.176 502 < /tmp/mbreq.bin | xxd
```
**Расшифровка ответа:**
| Ответ | Значение |
|---|---|
| `... 01 03 02 XXXX` | ✅ нормальный ответ (FC=03, 2 байта данных) |
| `... 01 83 04` | ❌ **SLAVE DEVICE FAILURE** — устройство есть, но не ответило |
| `... 0b 83 0b` | ❌ **GATEWAY TARGET DEVICE FAILED TO RESPOND** — mbusd передал, шина молчит (нет устройства/нет провода) |
> Exception-код = байт FC с флагом `0x80`; второй байт — код ошибки. Для заслонок вентиляции **slave = 11** (`configuration.yaml`, секция `modbus`).
##### ⏸️ ИТОГ: заслонки вентиляции — АППАРАТНЫЙ блокер (за Alex)
mbusd-стек **исправен полностью**: TCP отвечает, serial открыт (`/dev/serial/by-path/pci-0000:00:12.0-usb-0:4:1.0-port0`), HA-коннект с `192.168.2.176` держится. Но на запрос к slave 11 шина отдаёт **exception 0x0B** — устройство не отвечает.
**Диагноз: CH340 #2 воткнут в USB-порт t610, но линии A/B вентиляционной шины к нему не подключены (или шина обесточена).**
Это ровно тот блокер, о котором Alex предупреждал в начале сессии («проверь USB основной шины, дальше подключу ZONT»). **Никакие конфиги тут не помогут — нужна физика.** Заслонки оживут сами, как только шина будет подключена. **Адреса записаны:**
```
/dev/serial/by-path/pci-0000:00:12.0-usb-0:4:1.0-port0 (ttyUSB1, CH340 #2) = ВЕНТИЛЯЦИЯ (slave 11)
/dev/serial/by-path/pci-0000:00:12.0-usb-0:3:1.0-port0 (ttyUSB0, CH340 #1) = ZONT
```
⚠️ **Мораль для будущих переносов HA:** либо переносить `core.config_entries` целиком вместе с реестрами (тогда `device_id` согласуются), либо **после переноса обязательно перемапить `device_id`** в `automations.yaml`/`scripts.yaml` по `identifiers`, **и заодно проверить hex-ссылки `entity_id`**. Мы выбрали не переносить `core.config_entries` (чтобы сохранить MQTT-интеграцию t610) — отсюда и разрыв.
@@ -689,21 +776,27 @@ cp /tmp/reg.new.json "$REG"; chown root:root "$REG"; chmod 644 "$REG"
> 📌 Дашборд ссылается на сущности по человеческим именам, которые уже есть в реестре (`switch.sauna`, `light.smart_light_office_left`, `light.smart_light_stairs_l1`, `binary_sensor.shower_2_presence_sensor_presence`). После шага 8 всё оживёт.
#### 📍 СОСТОЯНИЕ НА КОНЕЦ СЕССИИ 2026-09-14 (для следующей сессии)
#### 📍 СОСТОЯНИЕ НА КОНЕЦ СЕССИИ 2026-09-14 (поздняя) — для следующей сессии
**Факты (проверено API):** HA `http://192.168.2.176` → 200; z2m `started`, 14 устройств; реестр 319 сущностей, **hex = 0**; `light.*` (5 шт.) работают; MQTT-интеграция на месте; `switch_as_x` (4) восстановлены.
**Факты (проверено API):** HA `http://192.168.2.176` → 200; z2m `started`, 14 устройств; реестр 319 сущностей, **hex = 0**; `light.*` (5 шт.) работают; MQTT-интеграция на месте; `switch_as_x` (4) восстановлены; **автоматизации 16 шт.: 15 `on` + 1 `off` (0 `unavailable`)**; HTTP-варнинг устранён; modbus.host = `192.168.2.176`; modbus-bridge опрос работает (без 404).
**Счётчики живого API:** 233 сущности, `unavailable` 45, `unknown` 82.
**Счётчики живого API:** 233 сущности; `unavailable` 44 (из них **32 — заслонки вентиляции**, аппаратный блокер); `unknown` 69.
**🔴 ПЕРВООЧЕРЕДНОЕ (блокер) — ДИАГНОСТИКА ЗАВЕРШЕНА, ОСТАЛОСЬ ЗАЛИТЬ:** починить 13 автоматизаций `unavailable` — см. §«ПИТФОЛЛ: device_id ломаются при переносе реестра». **Маппинг `device_id` полный (9/9, 20 вхождений)**, файл-кандидат `~/tmp-t610/etap3-fix/automations.fixed.yaml` готов и проверен. **Осталось:** ① решить hex-`entity_id` `switch.0xa4c13873b5c1575b` (l1 или l2?); ② `light.0xa4c13882a4b42db0``light.bed_dimmer`; ③ `ha core stop` → залить → `ha core start`.
**Живые zigbee-датчики (проверено):** `sensor.office_temperature_sensor_temperature = 23.82`, `sensor.recirculation_pump_voltage = 221`, `sensor.light_sensor_stairs_illuminance = 556`, `sensor.heating_cable_plug_voltage = 222`.
**Далее:**
1. `scripts.yaml` — device-ссылок **0**, hex-`entity_id` **0** (проверено, чистить нечего).
2. `sensor.*_summary`добавить `|default(0)` в template-сенсоры `configuration.yaml` (косметика).
3. Проверить дашборд `home_plan` визуально (ссылки теперь человеческие).
**✅ Этап 3 ЗАКРЫТ.** Всё, что осталось — вне конфигов:
**⏸️ 1. ГЛАВНОЕ: заслонки вентиляции (32 `switch.*_damper` `unavailable`)АППАРАТНЫЙ блокер, за Alex.** Подключить линии A/B вентиляционной шины к CH340 #2 (`by-path ...0:4:1.0-port0`, slave 11) или проверить питание шины. После подключения заслонки оживут сами — конфиг уже верный. См. §«ИТОГ: заслонки вентиляции».
**Далее (не блокеры):**
1. `sensor.*_summary` — добавить `|default(0)` в template-сенсоры `configuration.yaml` (косметика; ошибки `round got invalid input 'unknown'` для `kids_*`/`bedroom_*` — уйдут сами, когда sniffer вентиляции пришлёт данные).
2. `switch.sauna` = `unknown` — розетка физически отключена (`lastSeen` 8+ ч), не баг.
3. Камера (§8 родительского плана).
4. Этап 4: Caddy upstream → t610, GPON-редирект → t610, отключить TrueNAS.
**Ключевые пути/скрипты сессии:** `~/tmp-t610/``stage3/out/` (staged комплект), `backups/` (2 tar.gz), `z2m-new-config.yaml`, `do_rename_jq.sh`, `add_switchasx.py`, `apply_switchasx.sh`, `fix_dash2.sh`, `ha_token.txt`, `t610-config-entries.json`. **Правка автоматизаций:** `~/tmp-t610/etap3-fix/``automations.fixed.yaml`, `devid_mapping.json`, `automations.yaml.bak-20260914-114235`, `truenas.device_registry`, `core.device_registry`, `core.entity_registry`, `scripts.yaml`. На t610: `/config/.storage/*.bak-*`, `/config/zigbee2mqtt/configuration.yaml.bak-*`, `/tmp/stage3-prev/`.
**Ключевые пути/скрипты сессии:** `~/tmp-t610/``stage3/out/`, `backups/`, `ha_token.txt`. **Этап 3 правки:** `~/tmp-t610/etap3-fix/``automations.fixed.yaml`, `devid_mapping.json`, `truenas.device_registry`, `core.device_registry`, `core.entity_registry`, `scripts.yaml`, `http.new.json`, `mb_bridge.py`, `config.template.tmpl`, `mbtest.sh`, `check_dampers2.sh`, `final_check.sh`, `restart_ha.sh`, `run_check.sh`, `token.env`, `q_dampers.jq`, `q_sensors.jq`. На t610: `/config/automations.yaml.bak-devid-*`, `/config/configuration.yaml.bak-http-*`, `/config/.storage/http.bak-*`, `/addons/modbus-bridge/*.bak-hex-*`.
**⚠️ Питфолл сессии (важный для будущих сессий):** Alex **устал апрувать** запуск python-скриптов (`execute_code` и `/usr/bin/python3 -c`) — ТРЕБУЕТ bash+jq/curl. Пользоваться shell-скриптами, python только когда без него никак (и предупреждать).
### Этап 4 — проверка и отключение TrueNAS
18. [ ] Чек-лист из родительского плана §6
@@ -736,6 +829,11 @@ cp /tmp/reg.new.json "$REG"; chown root:root "$REG"; chmod 644 "$REG"
- [x]**РЕШЕНО 2026-09-14 — `Mini Smart Switch 1` удалён из z2m** (`force: true`). Мёртвое: `lastSeen` 2026-01-26, `unavailable`, нет зоны, нигде не используется.
- [x]**УТОЧНЕНО 2026-09-14 — механизм связи сущностей:** HA связывает по `unique_id`, НЕ по `entity_id`. Смена `friendly_name` в z2m сохраняет человеческие `entity_id`. Прежнее опасение «всё пересоздастся» снято.
- [ ]**ОСТАЛОСЬ (последний шаг Этапа 3):** прописать `friendly_name` в z2m по таблице из §«КРИТИЧЕСКОЕ ОТКРЫТИЕ» (16 устройств), перезапустить z2m, убедиться, что `unknown`-сущности ожили (ожидаемо ~133 → минимум). Затем чистка hex-остатков (58 шт.) в HA.
- [x]**ВЫПОЛНЕНО 2026-09-14 (поздняя сессия) — автоматизации починены:** `device_id` перемаплены (9/9, 20 вхождений), hex-`entity_id` `light.0xa4c13882a4b42db0``light.bed_dimmer`. Результат: **16 автоматизаций, 15 `on` + 1 `off`, 0 `unavailable`**. Этап 3 закрыт.
- [x]**УСТРАНЕНО 2026-09-14 — HTTP-варнинг:** блок `http:` удалён из `configuration.yaml`, `trusted_proxies`/`use_x_forwarded_for` перенесены в `.storage/http`.
- [x]**ИСПРАВЛЕНО 2026-09-14 — modbus.host:** `127.0.0.1``192.168.2.176`.
- [x]**ИСПРАВЛЕНО 2026-09-14 — modbus-bridge 404:** hex-entity_id в коде аддона → человеческие + `ha addons rebuild`.
- [ ] ⏸️ **ГЛАВНЫЙ ОСТАВШИЙСЯ БЛОКЕР (аппаратный, за Alex):** 32 заслонки вентиляции `unavailable` — шина не отвечает (exception 0x0B). Подключить линии A/B к CH340 #2 (`by-path ...0:4:1.0-port0`, slave 11). Конфиг верный, оживут сами.
- [ ] Камера (§8 родительского плана) — не аддон, разбираться отдельно
- [ ] ⚠️ Незакреплённое: `sensor.0xa4c138f8da8bc478_voltage/energy/power/current` (11 hex-сущностей розетки Насос обратки) — проживут ли под новым `friendly_name` или создадутся дубли; проверить после шага 8.