Когда я впервые подключил агента к умному дому через MCP, ожидал простой эффект: «ну, будет еще один способ дергать API». На практике вышло иначе. MCP в osysHome оказался не транспортом, а рабочим интерфейсом для эксплуатации: с понятными сущностями, историей изменений, проверками перед записью и безопасным контуром для автоматизации.
Покажу это на живых примерах: без магии на слайдах, на реальных инструментах и бытовых сценариях.
Почему вообще MCP в доме полезен
Обычный путь автоматизации часто выглядит так:
-
пишем скрипт на коленке;
-
через месяц забываем, где и почему что-то менялось.
С MCP все иначе. Агент работает не с «сырыми URL», а с понятными инструментами предметной области:
-
osys_list_classesиosys_list_objectsдля инвентаризации; -
osys_get_propertyиosys_get_property_historyдля наблюдения; -
osys_call_methodиosys_set_propertyдля действий; -
osys_validate_method_codeиosys_run_method_dryдля безопасной разработки; -
osys_update_object/osys_update_classсif_matchдля управляемых изменений.
По ощущениям это как дежурный инженер для дома: сначала проверяет, потом действует.
Быстрый старт: что нужно, чтобы агент заговорил с osysHome
В MCPServer для osysHome все строится вокруг endpoint /api/mcp и JSON-RPC поверх HTTP.
Из практики я бы выделил три вещи:
-
Токен-авторизация (
Authorization: Bearer ...илиX-MCP-Token). -
Разделение прав (чтение отдельно, запись отдельно, управление отдельно).
-
Аудит неудачных попыток и контроль write-инструментов.
Это критично: дому нужен не «самый умный агент», а предсказуемый агент с ограниченными правами.
Как выглядит рабочий цикл агента
Я придерживаюсь простого рабочего цикла:
-
Обнаружить контекст — какие классы, объекты и связи есть сейчас.
-
Проверить гипотезу — история свойств, текущие значения, логи.
-
Подготовить действие — dry-run, валидация кода или шаблона.
-
Выполнить изменение — только после проверки.
-
Верифицировать — убедиться, что эффект наступил и не зацепил соседние сценарии.
Звучит банально, но именно это отделяет «игрушку» от рабочего инструмента.
Кейс 0. Самый простой: включить свет в гостиной
Запрос агенту человеческим языком:
«Включи свет в гостиной».
Что делает агент:
-
Находит целевой объект освещения (например,
Relay01— «Свет(гостиная)»). -
Вызывает безопасное действие через MCP (
osys_set_propertyилиosys_call_method). -
Проверяет, что новое состояние применилось.
Технически запрос выглядит так:
{ "tool": "osys_set_property", "arguments": { "property_name": "Relay01.status", "value": 1, "source": "MCPAgent" }}
Ответ агента:
«Свет в гостиной включен.
Объект:Relay01(Свет(гостиная)).
Новое состояние:status = 1.»
Сценарий простой, но с него и начинают: проверили базовую команду, убедились, что все управляется, и только потом переходят к аналитике и сложным режимам.
Кейс 1. Аналитика энергопотребления: где реально жрет, а где просто кажется
Запрос агенту человеческим языком:
«Покажи сводку по энергопотреблению всего дома: сколько сейчас, где пики и насколько нагрузка стабильна по группе силовых устройств».
Агент делает не один запрос, а целую цепочку:
-
находит все power-объекты (
Power01..Power13,PowerPlug*,TotalPower) — всего 17; -
берет агрегаты и текущие значения по
TotalPower.power; -
строит топ потребителей по текущим значениям
*.power.
Короткий ответ агента, уже обычным языком:
«Нашел 17 объектов энергомониторинга.
Сейчас суммарная мощность дома: 168.71 Вт (TotalPower.power, объектTotalPower— Общее энергопотребление).
За последний месяц средняя нагрузка: 442.93 Вт, пиковое значение: 4838.83 Вт.
Текущий топ потребителей:
`Power05` — «Мощность(детские)» — 17.0 Вт
`Power06` — «Мощность(компьютер)» — 4.0 Вт
`Power09` — «Мощность(свет в гостиной)» — 1.48 Вт Остальные power-каналы сейчас близки к 0. По среднемесячной базе топ по вкладу в фон: `Power05` (23.63 Вт), `Power06` (8.58 Вт), `Power09` (6.86 Вт), `Power11` — «Мощность(бойлер)» (4.43 Вт).»
Что агент предлагает для снижения потребления по этой аналитике:
-
Проверить, почему
Power05держит высокий среднемесячный фон; добавить расписание/автоотключение в ночные часы. -
Для
Power06(компьютер) включить сценарий «глубокий сон ночью» и отключение периферии по отсутствию активности. -
Для
Power11(бойлер) вынести нагрев в дешевые тарифные окна и ограничить верхний порог температуры. -
Добавить еженедельный отчет «топ-5 потребителей за 30 дней», чтобы видеть эффект изменений.
Практический смысл: это уже не «посмотреть на одно реле», а цельная картина энергопотребления дома плюс конкретный план оптимизации.
Кейс 2. Аналитика errors.log: не просто «есть ошибка», а что чинить прямо сейчас
Запрос агенту человеческим языком:
«Проверь, нет ли системных проблем за последний час. Смотри не только
errors.log, а несколько логов модулей, чтобы понять масштаб.»
Агент смотрит сразу несколько источников:
-
errors.log— системные stacktrace и сетевые ошибки; -
OpenHasp.log— ошибки интеграции устройства/шины; -
ESPHome.log— телеметрия и стабильность данных; -
Modules.log— фоновая активность ядра/плагинов.
Короткий ответ агента:
«Проблемы действительно системные, не в одном файле.
Вerrors.logвижу TLS-ошибку при обращении кapi.telegram.org(SSLError: UNEXPECTED_EOF_WHILE_READING).
ВOpenHasp.logповторяется ошибка разбора события (Error processing message: 'event').
При этомESPHome.logиModules.logвыглядят стабильными (регулярные INFO-записи без ошибок).
Значит, инцидент локализуется в двух интеграционных зонах: сеть/Telegram и обработка OpenHasp-сообщений.»
Что агент предлагает как фиксы:
-
Для Telegram/TLS — проверить цепочку proxy/SSL, таймауты и актуальность cert store на хосте.
-
Для OpenHasp — валидировать входящий payload на ключ
eventи логировать raw-пакет при его отсутствии. -
Добавить guard в обработчики: неполные сообщения не должны валить поток обработки.
Это не «магия ИИ», а обычная инженерная рутина, просто заметно быстрее.
Кейс 3. Устройства, которые давно не отвечают, и устройства с риском обслуживания
Инвентаризация без эксплуатационных флагов мало полезна. Нужна именно «карта риска».
Запрос агенту человеческим языком:
«Составь список: какие устройства давно не выходят на связь и каким скоро нужно обслуживание (батарейки/связь)».
Агент проходит по группе устройств и собирает единый список проблем:
-
устройства без связи по
alive; -
устройства с риском обслуживания по
*.batteryиminBattery; -
при необходимости добавляет контекст по
alive/aliveTimeout.
Короткий ответ агента:
«Сформировал список проблемных устройств.
Поalive = 0сейчас:
Door03— Дверь (лоджия)
Door07— Дверь(Саша)
Door08— Дверь(Ваня)
Door10— Дверь(шкаф 1)
Низкий заряд батареи:
Motion01— Движение(коридор) — 17%
Motion02— Движение(гостиная) — 17%
Зона внимания:Motion06— Движение(Саша) — 43%.
Рекомендация: сначала восстановить связь/питание по объектам сalive = 0, затем заменить батарейки вMotion01/02.»
Так получается не точечная проверка одного объекта, а нормальная сервисная ведомость.
Кейс 4. Выявление аномалий по истории: где поведение ушло от нормы
Вместо сложной ML-модели часто хватает базовой статистики + здравого смысла.
Запрос агенту человеческим языком:
«Найди аномалии по климату: где значения выбиваются из обычного диапазона, и что проверить первым делом».
Агент проверяет не один датчик, а весь пул Climat01..Climat09: берет текущее значение temp и сравнивает с историческим avg для каждого.
Короткий ответ агента:
«Проверил 9 климатических датчиков на отклонение от исторической базы.
Топ аномалий:
`Climat07` — «Климат(лоджия)»: 19.5°C при среднем 13.55°C (сильное положительное отклонение).
`Climat03` — «Климат(туалет)»: 23.8°C при среднем 23.03°C (умеренное отклонение).
`Climat05` — «Климат(Ваня)»: 24.3°C при среднем 23.56°C (умеренное отклонение). Для `Climat08` — «Климат (кухня)» — среднее не рассчиталось (`avg = null`), нужно проверить полноту истории. Рекомендация: проверить сценарии отопления/проветривания на лоджии и восстановить корректное накопление истории для кухонного датчика.»
То есть агент отдает не сырые числа, а приоритизированный список аномалий с понятными действиями.
Кейс 5. Новый режим «Кинотеатр»: включение и выключение под ключ
Это уже не аналитика, а реальное внедрение логики через MCP, где агент не просто «советует», а сам собирает рабочую сущность.
Запрос агенту человеческим языком:
«Сделай режим Кинотеатр: отдельный объект, метод включения и метод выключения. Перед запуском проверь код безопасно.»
1) Агент создает объект режима
{ "tool": "osys_add_object", "arguments": { "object_name": "CinemaMode", "class_name": "Modes", "description": "Режим кинотеатр", "update": true }}
2) Добавляем методы activate и deactivate
{ "tool": "osys_add_object_method", "arguments": { "object_name": "CinemaMode", "name": "activate", "description": "Включить сценарий кинотеатра", "code": "target = getProperty('targetBrightness')\nif target is None:\n target = 20\nprev = getProperty('Dimmer01.status')\nsetProperty('previousBrightness', prev, source='CinemaMode')\nsetProperty('active', 1, source='CinemaMode')\nsetProperty('sceneName', 'Cinema', source='CinemaMode')\nsetProperty('lastActivated', datetime.now(), source='CinemaMode')\nsetProperty('Relay15.status', 0, source='CinemaMode')\nsetProperty('Dimmer01.status', target, source='CinemaMode')\nsetProperty('Rgb05.status', 1, source='CinemaMode')\nsetProperty('Rgb05.brightness', target, source='CinemaMode')", "update": true }}
{ "tool": "osys_add_object_method", "arguments": { "object_name": "CinemaMode", "name": "deactivate", "description": "Выключить сценарий кинотеатра", "code": "prev = getProperty('previousBrightness')\nif prev is None:\n prev = 0\nsetProperty('active', 0, source='CinemaMode')\nsetProperty('Dimmer01.status', prev, source='CinemaMode')\nsetProperty('Rgb05.status', 0, source='CinemaMode')\nsetProperty('Relay15.status', 1, source='CinemaMode')", "update": true }}
3) Агент добавляет свойства объекта, чтобы режимом было удобно управлять
Чтобы режимом можно было пользоваться и в сценариях, и в интерфейсе, агент добавляет базовые свойства:
-
active(int) — текущий статус режима (0/1); -
targetBrightness(int) — яркость, которую пользователь задает для режима; -
previousBrightness(int) — яркость, которая была до включения режима; -
sceneName(str) — человекочитаемое имя сцены; -
lastActivated(datetime) — когда режим запускался последний раз.
Технически это выглядит так (пример для одного свойства):
{ "tool": "osys_add_object_property", "arguments": { "object_name": "CinemaMode", "name": "active", "type": "int", "description": "Статус режима кинотеатр", "update": true }}
По аналогии агент добавляет остальные свойства (targetBrightness, previousBrightness, sceneName, lastActivated).
4) Итог: что именно создал агент (с кодом методов)
После выполнения шагов выше в системе появляется новый объект:
-
Объект:
CinemaMode— «Режим кинотеатр» -
Класс:
Modes -
Свойства:
active,targetBrightness,previousBrightness,lastActivated -
Методы:
activate,deactivate
Код метода activate:
target = self.getProperty('targetBrightness')if target is None: target = 20prev = getProperty('Dimmer01.status')self.setProperty('previousBrightness', prev, source='CinemaMode')self.setProperty('active', 1, source='CinemaMode')self.setProperty('lastActivated', datetime.now(), source='CinemaMode')setProperty('Relay15.status', 0, source='CinemaMode')setProperty('Dimmer01.status', target, source='CinemaMode')setProperty('Rgb05.status', 1, source='CinemaMode')setProperty('Rgb05.brightness', target, source='CinemaMode')
Код метода deactivate:
prev = self.getProperty('previousBrightness')if prev is None: prev = 0self.setProperty('active', 0, source='CinemaMode')setProperty('Dimmer01.status', prev, source='CinemaMode')setProperty('Rgb05.status', 0, source='CinemaMode')setProperty('Relay15.status', 1, source='CinemaMode')
5) Проверяем перед публикацией
-
osys_validate_method_code— синтаксис и ограничения runtime. -
osys_run_method_dry— dry-run без побочных эффектов.
Именно так можно проверить, что созданные свойства реально используются, а не просто «задекларированы»:
{ "tool": "osys_run_method_dry", "arguments": { "object_name": "CinemaMode", "code": "target = getProperty('targetBrightness')\nif target is None:\n target = 20\nprev = getProperty('Dimmer01.status')\nsetProperty('previousBrightness', prev, source='CinemaMode')\nsetProperty('active', 1, source='CinemaMode')\nsetProperty('sceneName', 'Cinema', source='CinemaMode')\nsetProperty('lastActivated', datetime.now(), source='CinemaMode')\nsetProperty('Dimmer01.status', target, source='CinemaMode')" }}
Ожидаемый результат проверки: в captured_actions будут ключевые действия по свойствам:
-
active -
targetBrightness -
previousBrightness -
lastActivated
Практический смысл этой схемы:
-
Пользователь заранее задает
targetBrightness(например, 12 или 20). -
На
activateагент применяет именно это значение. -
Перед применением агент сохраняет текущую яркость в
previousBrightness. -
На
deactivateяркость возвращается кpreviousBrightness, то есть в состояние «как было до кинотеатра».
И только после этого режим стоит включать в рабочий сценарий.
Так получается полноценный режим с предсказуемым включением и аккуратным откатом.
Что важно по безопасности, если пускаете агента в дом
Ниже набор правил, который у меня реально работает:
-
перед любой работой агента с write-операциями делайте бэкап (минимум БД и критичных конфигов) и проверяйте, что восстановление реально работает;
-
выдавайте агенту read-only токен по умолчанию;
-
write-права открывайте только под конкретные задачи;
-
отдельно ограничивайте dangerous-инструменты (массовые апдейты, удаление сущностей);
-
все изменения через этап «validate/dry-run»;
-
ведите журнал «кто/что/когда» менял.
Главная мысль: не «слепо доверять агенту», а строить контур, где ошибка локальна и обратима.
Ограничения и анти-паттерны
Что делать не стоит:
-
давать полные write-права 24/7 «потому что так удобнее»;
-
смешивать диагностику и изменение состояния в одном автоматическом шаге;
-
обновлять классы/объекты без ревизий и проверки актуальности;
-
считать dry-run «лишней формальностью».
С агентами правило простое: чем аккуратнее дисциплина в начале, тем меньше ночных приключений потом.
Итого
MCP в osysHome для меня — это не про «поговорить с домом на естественном языке».
Это скорее ощущение, что рядом появился спокойный и внимательный технапарник: ты формулируешь задачу обычными словами, а в ответ получаешь не магию, а понятный, проверяемый результат.
В повседневном использовании это очень чувствуется. Раньше многие вещи откладывались «на потом», потому что нужно было вручную пройтись по данным, логам, связям и не забыть ничего сломать. С MCP этот путь стал короче и заметно спокойнее: меньше рутины, меньше дерганых правок, больше уверенности в том, что система под контролем.
И вот здесь для меня случился главный сюрприз.
В начале я ожидал «удобный интерфейс к API». На выходе получил заметно больше: агент реально берет на себя кусок рутинной инженерной работы — от диагностики до безопасного внедрения изменений.
Если честно, это и есть тот самый вау-эффект: результат оказался намного сильнее стартовых ожиданий.
ссылка на оригинал статьи https://habr.com/ru/articles/1027806/