Практика: Создание I/O Map для учебного стенда
Введение: Цели и задачи картирования учебного стенда
На данном практическом занятии мы перейдем от теории к реальным действиям и создадим Карту Входов-Выходов (I/O Map) для нашего учебного стенда. Эта работа — один из ключевых этапов пусконаладки любого объекта автоматизации.
> 🔗 Связанный материал: Мы подробно рассмотрели теоретические основы и назначение I/O Map в уроке COURSE-03-M04-L01 "Что такое карта входов-выходов (I/O Map)". Рекомендуется освежить эти знания перед началом практики.
Основная цель I/O Map — создать единый, исчерпывающий документ, который служит «переводчиком» между физическим миром (провода, клеммы, устройства) и программной логикой контроллера (сценарии Node-RED, MQTT-топики). Это — ваш главный навигационный инструмент при монтаже, настройке и, что особенно важно, при последующей диагностике и обслуживании системы.
Для нашего занятия мы будем использовать типовой учебный стенд, имитирующий автоматизацию небольшой комнаты. В состав стенда входит следующее оборудование, подключенное к контроллеру HI:
- Исполнительные устройства (Выходы):
* Управляемая розеточная группа: Подключена к реле контроллера.
* Привод шторы: Управляется двумя реле контроллера для команд «Открыть» и «Закрыть».
* Дополнительные группы света: Подключены через внешний 6-канальный релейный модуль по шине RS-485 (Modbus RTU).
* Диммируемая светодиодная лента: Подключена через внешний модуль диммирования по шине RS-485 (Modbus RTU).
- Управляющие устройства и датчики (Входы):
* Цифровой датчик температуры: DS18B20, подключен к универсальному входу контроллера по шине 1-Wire.
* Датчик открытия двери (геркон): Подключен к универсальному входу контроллера в режиме «сухой контакт».
Наша конечная цель — пройти все этапы картирования и получить на выходе готовую таблицу I/O Map. Этот документ должен однозначно отвечать на следующие вопросы для каждого элемента системы:
Эта практика заложит фундамент для быстрой и безошибочной настройки всего объекта.
---
Шаг 1: Картирование физического уровня (Physical Layer)
Первый и самый важный шаг — это инвентаризация и документирование всех устройств, которые напрямую подключены к клеммам ввода-вывода нашего контроллера HI.
> ⚠️ Внимание: Перед началом любых работ по физическому подключению, проверке контактов и маркировке кабелей всегда убеждайтесь, что контроллер и все подключаемое оборудование полностью обесточены. Работы на клеммах под напряжением опасны для жизни и могут привести к выходу оборудования из строя.
Процесс картирования физического уровня состоит из двух частей: инвентаризации и документирования.
Проведение инвентаризации
Осмотрите стенд и составьте список всех устройств, подключенных непосредственно к контроллеру. Следуя методологии, рассмотренной в уроке COURSE-03-M04-L02 "Система именования и маркировки", присвоим каждому устройству уникальный идентификатор (UID).
Пример списка для нашего стенда:- Выходы (Нагрузки):
* `LIGHT-WALL-01`: Настенные бра
* `SOCKET-DESK-01`: Управляемая розетка у стола
* `CURTAIN-LIVING-01`: Привод шторы в гостиной
- Входы (Датчики и выключатели):
* `SW-WALL-01`: Выключатель для настенных бра
* `TEMP-LIVING-01`: Датчик температуры в гостиной (DS18B20)
* `DOOR-ENTRY-01`: Датчик открытия входной двери (геркон)
Составление таблицы подключений
Теперь занесем эту информацию в таблицу, точно указав, к какой клемме контроллера HI подключен каждый провод. Эта таблица — основа физического уровня нашей I/O Map.
| ID Устройства (UID) | Тип устройства | Подключение к контроллеру HI | Маркировка кабеля | Примечание |
| :--- | :--- | :--- | :--- | :--- |
| Выходы | | | | |
| `LIGHT-CEILING-01` | Группа света (230В) | `RL-01` | `CBL-L-01` | Управляет контактором KМ1 |
| `LIGHT-WALL-01` | Группа света (230В) | `RL-02` | `CBL-L-02` | 3 светильника по 15Вт |
| `SOCKET-DESK-01` | Розеточная группа | `RL-03` | `CBL-S-01` | Линия для настольной лампы, до 500Вт |
| `CURTAIN-LIVING-01` | Привод шторы (230В) | `RL-04` (Open), `RL-05` (Close) | `CBL-M-01` | Требуется логика "защиты от одновременного включения" |
| Входы | | | | |
| `SW-CEILING-01` | Кнопочный выключатель | `UI-01`, `GND` | `CBL-SW-01` | Режим "сухой контакт" (DI) |
| `SW-WALL-01` | Кнопочный выключатель | `UI-02`, `GND` | `CBL-SW-02` | Режим "сухой контакт" (DI) |
| `DOOR-ENTRY-01` | Геркон | `UI-10`, `GND` | `CBL-SEN-01` | Режим "сухой контакт" (DI). Состояние NC. |
| `TEMP-LIVING-01` | Датчик температуры | `UI-15` (1-Wire Data) | `CBL-SEN-02` | DS18B20, требуется подтяжка к +3.3В |
На этом этапе мы задокументировали все "прямые" подключения. Мы точно знаем, что замыкание на клемме `UI-01` означает нажатие на выключатель `SW-CEILING-01`, а подача напряжения на катушку реле `RL-02` включит свет `LIGHT-WALL-01`. Эта таблица станет неотъемлемой частью исполнительной документации проекта.
---
Шаг 2: Картирование устройств на шине RS-485 (Modbus RTU)
Теперь перейдем к устройствам, которые общаются с контроллером не напрямую, а через промышленную шину данных RS-485 по протоколу Modbus RTU. К таким устройствам на нашем стенде относятся внешний релейный модуль и модуль диммирования.
> 💡 Подсказка: Прежде чем писать сложную логику в Node-RED, всегда проверяйте связь с Modbus-устройствами с помощью утилит командной строки Linux. Утилита `mbpoll`, установленная на контроллер HI, позволяет быстро опросить устройство и убедиться, что физическое подключение, Slave ID и параметры шины (скорость, четность) настроены верно.
Присвоение адресов и работа с документацией
Каждое устройство на шине Modbus должно иметь уникальный адрес (Slave ID).
* 6-канальный релейный модуль: `Slave ID = 10`
* 3-канальный модуль диммирования: `Slave ID = 11`
* Для релейного модуля (ID=10):
* Управление реле 1-6 обычно осуществляется записью в Coils (регистры типа 0x). Адреса: `0` (Реле 1), `1` (Реле 2), ..., `5` (Реле 6).
* Запись `true` в `Coil 0` включит первое реле.
* Чтение статуса реле 1-6 — из Discrete Inputs (регистры типа 1x) с адресами `0`...`5`.
* Для модуля диммирования (ID=11):
* Управление яркостью канала 1 часто находится в Holding Registers (регистры типа 4x). Например, адрес `128` отвечает за яркость (значение `0` - `100`).
* Включение/выключение канала 1 может быть в соседнем регистре. Например, `Holding Register 129` (значение `0` — выкл, `1` — вкл).
Создание таблицы Modbus-адресации
Систематизируем эту информацию в таблице. Также присвоим UID новым логическим устройствам.
| ID Устройства (UID) | Тип устройства | Slave ID | Тип регистра | Адрес | Функция |
| :--- | :--- | :--- | :--- | :--- | :--- |
| `LIGHT-SPOT-01` | Точечный свет, зона 1 | 10 | Coil (Запись) | 0 | Вкл/Выкл |
| `LIGHT-SPOT-01` | Точечный свет, зона 1 | 10 | Discrete Input (Чтение) | 0 | Статус Вкл/Выкл |
| `LIGHT-SPOT-02` | Точечный свет, зона 2 | 10 | Coil (Запись) | 1 | Вкл/Выкл |
| `LIGHT-SPOT-02` | Точечный свет, зона 2 | 10 | Discrete Input (Чтение) | 1 | Статус Вкл/Выкл |
| `LIGHT-DIM-01` | Диммируемая LED-лента | 11 | Holding Register (Запись) | 128 | Установка яркости (0-100) |
| `LIGHT-DIM-01` | Диммируемая LED-лента | 11 | Holding Register (Запись) | 129 | Вкл(1)/Выкл(0) |
| `LIGHT-DIM-01` | Диммируемая LED-лента | 11 | Input Register (Чтение) | 200 | Текущая яркость (статус) |
Теперь у нас есть четкое понимание, как адресоваться к каждому из внешних устройств.
Практический пример: `mbpoll` и Node-RED
Давайте проверим связь с релейным модулем. Подключимся к контроллеру по SSH и выполним команду:
# Опросить состояние первого Coil (адрес 0) на устройстве с Slave ID 10.
# Используем порт /dev/ttyS1 (один из портов RS-485 контроллера HI).
# Скорость шины - 9600 бод.
# -a 10 (Slave ID)
# -b 9600 (Baud rate)
# -t 1 (function code 1, 'read coils')
# -r 0 (register address)
# -c 1 (count of registers to read)
mbpoll -a 10 -b 9600 /dev/ttyS1 -t 1 -r 0 -c 1
Если вы видите в ответ `[0]` или `[1]`, значит, связь есть.
В Node-RED для включения этого реле мы используем узел `Modbus-Write`. Его настройка будет выглядеть так:
- Имя: `Включить LIGHT-SPOT-01`
- Server: `(Ваш настроенный Modbus RTU клиент для /dev/ttyS1)`
- Unit-ID: `10`
- FC (Function Code): `FC 5: Force Single Coil`
- Address: `0`
- Value: `msg.payload` (где в `msg.payload` мы будем передавать `true` или `false`)
Мы успешно связали физический мир Modbus с миром Node-RED.
---
Шаг 3: Программный уровень — создание MQTT-топиков в Node-RED
На этом шаге мы создаем финальный, логический уровень абстракции. Мы "спрячем" все сложности физических и шинных адресов за простыми и понятными MQTT-топиками. Любой компонент системы (мобильное приложение, голосовой ассистент, другой контроллер) будет общаться с нашими устройствами через MQTT, не зная ничего об их внутреннем устройстве.
Мы будем использовать стандартную структуру именования, разобранную ранее: `проект/локация/класс_устройства/id/действие`. Для нашего стенда она будет выглядеть как `hi/stand/light/ceiling-01/set`.
Трансляция адресов в топики
Наша задача — создать в Node-RED потоки, которые будут выполнять эту трансляцию:
* Сообщение `ON` в топик `hi/stand/light/ceiling-01/set` должно активировать реле `RL-01`.
* Сообщение `ON` в топик `hi/stand/light/spot-01/set` должно инициировать Modbus-запись `true` в `Coil 0` на устройстве с `ID=10`.
* Сообщение с числом `75` в топик `hi/stand/light/dim-01/brightness/set` должно инициировать Modbus-запись значения `75` в `Holding Register 128` на устройстве с `ID=11`.
* Нажатие на физический выключатель `SW-CEILING-01` (подключен к `UI-01`) должно публиковать сообщение, например `CLICK`, в топик `hi/stand/switch/ceiling-01/status`.
* После успешного включения света `LIGHT-SPOT-01` через Modbus, Node-RED должен опубликовать `ON` в топик `hi/stand/light/spot-01/status`.
* При изменении состояния геркона `DOOR-ENTRY-01` на `UI-10`, Node-RED должен опубликовать `OPEN` или `CLOSED` в `hi/stand/sensor/door/entry-01/status`.
Пример реализации в Node-RED
Рассмотрим пример потока, который опрашивает модуль диммирования и публикует его статус в несколько MQTT-топиков.
Схема потока:`[Inject]` -> `[Modbus-Getter]` -> `[Function: Parse Dimmer Status]` -> `[Switch: route by topic]` -> `[MQTT Out]`
На вход этого узла приходит массив. Допустим, `msg.payload.data = [80, 1]`, где `80` — текущая яркость, `1` — состояние "Включено".
// Получаем массив данных от Modbus-узла
const data = msg.payload.data;
// Валидация ответа
if (!Array.isArray(data) || data.length < 2) {
node.error("Некорректный ответ от модуля диммирования", msg);
return null;
}
const brightness = data[0];
const state = data[1];
// Формируем сообщения для отправки в MQTT
// Сообщение 1: Статус яркости
const msg_brightness = {
topic: "hi/stand/light/dim-01/brightness/status",
payload: brightness
};
// Сообщение 2: Статус Вкл/Выкл
const msg_state = {
topic: "hi/stand/light/dim-01/status",
payload: (state === 1) ? "ON" : "OFF"
};
// node.send() может отправлять несколько сообщений
// Каждое сообщение пойдет дальше по потоку независимо
node.send([msg_brightness, msg_state]);
return null; // т.к. мы уже сами отправили сообщения через node.send()
Таким образом, мы создали полную связь между аппаратным миром и программной шиной сообщений MQTT, полностью абстрагировавшись от деталей реализации.
---
Шаг 4: Сведение данных в итоговую Карту Входов-Выходов
Теперь, когда мы проанализировали все уровни — физический, шинный и программный — настало время свести всю информацию в единый, финальный документ. Это и есть наша I/O Map.
> 💡 Подсказка: Для ведения I/O Map в команде инженеров идеально подходят облачные электронные таблицы, такие как Google Sheets или Microsoft Excel Online. Они позволяют организовать совместный доступ, отслеживать историю изменений и иметь актуальную версию документа, доступную с любого устройства.
Структура финальной таблицы
Итоговая таблица должна быть максимально информативной и связывать все ранее собранные данные.
Структура столбцов:- Логическое имя: Понятное человеку название устройства.
- ID устройства (UID): Уникальный системный идентификатор.
- Тип устройства: Например, "Реле", "Диммер", "Кнопочный выключатель".
- Физическое подключение (Клемма): Клемма на контроллере HI или модуле расширения.
- Шинный адрес (ID:Регистр): Для устройств Modbus, CAN и др.
- MQTT Команда (`/set`): Топик для отправки команд управления.
- MQTT Статус (`/status`): Топик для получения обратной связи.
- Примечание: Любая дополнительная важная информация (мощность, модель устройства, особенности логики).
Пример заполненной I/O Map для нашего стенда
| Логическое имя | ID устройства (UID) | Тип устройства | Физическое подключение | Шинный адрес (ID:Регистр) | MQTT Команда (`.../set`) | MQTT Статус (`.../status`) | Примечание |
| :--- | :--- | :--- | :--- | :--- | :--- | :--- | :--- |
| Потолочный свет | `LIGHT-CEILING-01` | Реле (Контроллер) | `RL-01` | - | `.../light/ceiling-01/set` | `.../light/ceiling-01/status` | 230В, до 16А |
| Выключатель потолка | `SW-CEILING-01` | Кнопочный выключатель | `UI-01`, `GND` | - | - | `.../switch/ceiling-01/status` | Сигнал CLICK/DBLCLICK/LONG |
| Точечный свет, зона 1 | `LIGHT-SPOT-01` | Реле (Modbus) | - | `10:Coil0` (W), `10:DI0` (R) | `.../light/spot-01/set` | `.../light/spot-01/status` | Модуль WB-MR6, Реле 1 |
| LED-подсветка | `LIGHT-DIM-01` | Диммер (Modbus) | - | `11:HR128` (яркость) | `.../light/dim-01/brightness/set` | `.../light/dim-01/brightness/status` | Модуль WB-MDM3, Канал 1 |
| LED-подсветка (Вкл/Выкл) | `LIGHT-DIM-01` | Диммер (Modbus) | - | `11:HR129` (состояние) | `.../light/dim-01/set` | `.../light/dim-01/status` | Связан с яркостью |
| Датчик температуры | `TEMP-LIVING-01` | Датчик 1-Wire | `UI-15` | - | - | `.../sensor/temperature/living-01/status` | DS18B20 |
| Датчик двери | `DOOR-ENTRY-01` | Геркон ("сухой контакт") | `UI-10`, `GND` | - | - | `.../sensor/door/entry-01/status` | NC (нормально-замкнутый) |
Этот документ является результатом нашей работы. Крайне важно поддерживать его в актуальном состоянии. Любое изменение в физическом подключении или программной логике должно немедленно отражаться в I/O Map. Введите версионирование файла (например, `IO_Map_Stand_v1.0.xlsx`), чтобы всегда можно было понять, какая версия документа соответствует текущей конфигурации.
---
Заключение: Проверка и использование I/O Map
Мы завершили полный цикл создания Карты Входов-Выходов, пройдя четыре ключевых шага:
Теперь у вас в руках мощнейший инструмент, но его ценность проявится только при правильном использовании.
Валидация I/O Map
Прежде чем сдавать объект, необходимо проверить (валидировать) карту. Это процесс пошаговой проверки соответствия документа реальной конфигурации.
* Строка `LIGHT-CEILING-01`: Опубликуйте сообщение `ON` в топик `hi/stand/light/ceiling-01/set`. Убедитесь, что:
a) Физически включился потолочный свет.
b) В топик `hi/stand/light/ceiling-01/status` пришло сообщение `ON`.
* Строка `SW-CEILING-01`: Нажмите на физический выключатель. Убедитесь, что:
a) В топике `hi/stand/switch/ceiling-01/status` появилось соответствующее сообщение.
b) Свет `LIGHT-CEILING-01` изменил свое состояние (если такая логика настроена).
* Строка `LIGHT-DIM-01`: Опубликуйте `50` в `.../brightness/set`. Убедитесь, что:
a) Лента загорелась на половину яркости.
b) В `.../brightness/status` пришло значение `50`.
Этот процесс, по сути, является частью Smoke Test для всей системы и гарантирует, что ваша документация на 100% соответствует действительности.
Использование I/O Map в работе
- Пусконаладка: I/O Map — это ваш чек-лист. Проверив каждую строку, вы можете быть уверены, что все базовые функции системы работают корректно.
- Диагностика: Представьте, что клиент сообщает: «У меня не работает подсветка». Вы открываете I/O Map, находите строку `LIGHT-DIM-01` и мгновенно получаете всю информацию: это Modbus-устройство с `ID=11`, управляется через `HR128`. Вы не тратите время на проверку реле контроллера или других модулей. Ваши действия становятся целенаправленными: проверить шину RS-485, питание модуля `ID=11`, использовать `mbpoll` для прямой отправки команды. Время на поиск неисправности сокращается с часов до минут.
- Обслуживание и модернизация: Когда через год на объект придет другой инженер, ему не придется «прозванивать» сотни проводов. I/O Map станет для него исчерпывающим руководством по архитектуре системы, позволяя быстро и безопасно вносить изменения или добавлять новые функции.
Что дальше?
Вы освоили один из самых важных практических навыков инженера по автоматизации. В следующем модуле мы перейдем к написанию более сложных сценариев в Node-RED, используя созданную нами I/O Map как основу для взаимодействия с оборудованием. Вы увидите, как правильно структурированная карта упрощает создание комплексной логики автоматизации.