Кажется вопрос этот задавали много раз, но кажется тема достаточно “непрозрачная”, чтобы понять детально этот механизм самостоятельно.
Какие правила запускаются при запуске контроллера? Вижу, что крон-правила стартуют, а как насчёт тех, которые в виде:
defineRule(“start_stop_button”, {
whenChanged: “sauna_thermostat/status”,
then: function(newValue) {
где sauna_thermostat - виртуальное устройство? Этот Rule не стартанул, т.к. при запуске движок считает что значение sauna_thermostat/status не изменилось?
Короче говоря, требуется детальное понимание, как и когда срабатывают правила на запуске. Документацию читал много раз, все равно непонятно.
Всё-таки есть минус правил, основанных на event-driven подходе: сложно контролировать статус этого правила (работает или нет - не видно, кроме как через дебаг).
Из-за ошибки в коде и сложности поведения Rule в этой части моя пока ещё “виртуальная” сауна включила ТЭНы и после перезагрузки контроллера. Это небезопасно.
Это может означать что если во время работы сауны выключат свет и покинуть сауну, то после подачи питания сауна может запуститься сама.
В этой связи хочу сказать, что возможно безопаснее все же использовать forceddefault = true (т.е. значение по умолчанию), т.к. это по умолчанию более безопасное состояние.
Все правила активны сразу после объявления. Механизм там простой: правило подписывается на топик, указанный в триггере (whenChanged, asSoonAs…). Если говорить про триггер whenChanged, то он не сработает на первое значение, которое опубликуется в топик при инициализации виртуального устройства (или на получение retain-значения, если оно в топике уже хранится). На все последующие значения - сработает.
Тут какая ситуация. У меня к параметру будет жестко привязан физический выход. По-умолчанию настроено так, что после перезагрузки параметры возвращаются в прежнее состояние.
Обычно именно по-умолчанию система настраивается так, что перезагрузка решающего устройства сбрасывает все состояния\сигналы выключенное состояние.
Т.е. в 99% случаев это приводит к “остановкам” и “отключениям” оборудования. Включение в “последнее” состояние как раз несёт риск, что входы\выходы\параметры остаются в прежнем состоянии, а логическое состояние программы находится в другом режиме (грубо говоря программа может быть в режиме “ожидания”, но при этом выходы уже самопроизвольно включились).
Я бы предложил все-таки везде, где пользователь может выстрелить себе в ногу - по-умолчанию выбирать более безопасный вариант, а не более “удобный”.
Я думаю, вас одолели пользователи, жалующиеся, что все их параметры сбрасывались после перезагрузки и вы посчитали, что удобнее по умолчанию сделать восстановление их значений в состояние до перезагрузки.
Но это “хорошо работает” до той поры, пока я к параметру не привяжу какой-то физический выход. Интуитивно лично я ожидал, что при перезагрузке параметры все-таки сбросятся. Решил проверить. Был весьма удивлен, что этого не произошло и полез читать документацию.
Предлагаю пересмотреть этот механизм))
Если у вас виртуальное устройство управляет физическим аппаратом, который может быть источником неприятностей, я бы рекомендовал такую логику его работы:
Настроить безопасное состояние релейного Modbus-модуля: нет связи - выключаем ТЭНы.
Виртуальное устройство, сразу после его создания, должно проверить доступность (isControlExists, meta/error) того контрола, которым включаются ТЭНы. Если контрол недоступен - подписываемся на топик и ждем, когда станет доступен, больше ничего не делаем.
Если контрол реле доступен - сразу читаем текущее состояние. Проверяем доступность остальных контролов, влияющих на состояние реле. Если чего-то не хватает - выключаем реле (если включено), подписываемся на топики, ждем, когда появится все необходимое. Если всего хватает - проверяем условия, приводим реле к тому состоянию, которое должно быть по нашим условиям.
Подписываемся на топики /meta/error всех физических устройств. Связь с чем-то пропала - выключаем реле, если можем (если не можем - выключится само при отсутствии связи). Появилась - повторяем п.3.
Подписываемся на топики сенсоров, кнопок, задаем логику поведения реле в зависимости от состояния всего остального.
Банальных решений тут быть не может - одним/двумя правилами не отделаешься. Надо держать в голове все возможные ситуации: может пропасть связь, может рестартовать драйвер, в момент инициализации виртуального устройства топики физических устройств могут еще отсутствовать, может перезагрузиться wb-rules. И на все это надо адекватно реагировать, wb-rules за вас это не сделает.
Спасибо. Буду переваривать. К сожалению, действительно довольно много вещей, помимо “процессной части” необходимо контролировать, а это всё повышает риск…
Был бы признателен, если кто-то смог бы поделиться “безопасным обработчиком”, который обвязывает все действия проверками на ошибки и т.д…
Для термостата сауны я еще рассматриваю вариант загнать исполнение все-таки в cron @1s и работать в цикле, т.к. все-таки циклу как-то больше доверия. Скрипт WhenChanged слишком уж мудрёный и приходится контролировать все неочевидные моменты. Плюс нужно еще контролировать “побочную нагрузку” (а существует ли топик, а есть ли связь, а загрузились ли скрипты и т.п.)…
За ваши рекомендации в любом случае спасибо, но там еще не описан сценарий перезагрузки контроллера; я вынес вопрос в отдельный топик, связанный с тем, что все контролы при дефолтном описании виртуального устройства (без явного прописывания forcedDefault) - все контролы восстанавливают своё предыдущее состояние (или я все-таки ошибаюсь?), а это переводит всю программу в “непонятное” состояние (типа автоматический режим включен и т.п.).
Как это работает? Кто загружается первый, кто второй? Максимум я где-то встречал, что JS rule загружаются по алфавиту, но кто первее - виртуальные или физические устройства?..
Я уже думал и про то, что структуру rule выстроить таким образом, чтобы первым запускался создатель виртуальных устройств и только потом “бизнес логика”. Обмазывать логику управления тысячей проверок на каждый чих - слишком как-то избыточно получается…
Файлы со скриптами обрабатываются по алфавиту, тут все в ваших руках. Значения в топики от устройств пишут драйверы (и другие службы контроллера), действуют они с wb-rules асинхронно, предсказать порядок появления значений невозможно. Поэтому контролировать наличие связи с устройством посредством meta/error необходимо.