Более года назад я наткнулся на технологию передачи текстовых данных по радио — Meshtastic. Решил её попробовать, но «пощупать руками» переросло в проект автономного уличного узла на солнечной панели. Всё работало — пока я не решил добавить метрики энергопотребления.

И тогда узел ушёл в офлайн на полгода. Причина оказалась настолько же простой, насколько обидной. История о том, как хаос в отладке стоил шести месяцев, а спасение пришло от малинки (Raspberry Pi 2), паяльника и правила, которое я сам проповедую своим инженерам.

Привет, Хабр! Меня зовут Сизов Сергей, я технический директор продукта Deckhouse Solution Support в компании «Флант». Вообще я не специалист в вопросах радиоэлектроники — скорее начинающий радиолюбитель. Поэтому сквозь тернии к звёздам изучаю всё на ходу в своё свободное время и в удовольствие!

Что такое Meshtastic

Meshtastic — это децентрализованная сеть, которая использует Lora в качестве транспорта и позволяет обмениваться текстовыми сообщениями. По большому счёту это как мессенджер, для которого не нужен интернет.

Не сказать, что это новшество, но мне понравилось, что этой технологии не нужен интернет и что она базируется на LoRaWan. И то, что узлы собираются в mesh-сеть.

Схема показывает архитектуру mesh-сети на базе Meshtastic-устройств: как разные клиентские устройства (смартфоны, ноутбук, портативный терминал) подключаются к LoRa-узлам по локальным протоколам (Bluetooth, USB, Wi-Fi), а сами узлы передают данные друг другу на дальние расстояния через радиоканал LoRa, образуя децентрализованную mesh-сеть связи
Схема показывает архитектуру mesh-сети на базе Meshtastic-устройств: как разные клиентские устройства (смартфоны, ноутбук, портативный терминал) подключаются к LoRa-узлам по локальным протоколам (Bluetooth, USB, Wi-Fi), а сами узлы передают данные друг другу на дальние расстояния через радиоканал LoRa, образуя децентрализованную mesh-сеть связи

Сейчас это скорее проект для энтузиастов, но, возможно, он найдёт применение в сфере туризма или МЧС.

К слову, на текущий момент зафиксирована передача данных напрямую между двумя узлами, разумеется с направленными антеннами, на 331 км.

Начало: как я пришёл к идее об автономном узле

Я решил попробовать, купил несколько модулей на частоте 433 МГц, поставил прошивку, поигрался — сообщения бегают. Зачем? Да Ктулху его знает! Я ж инженер, мне интересно потрогать технологию своими руками. 

Я даже вступил в Telegram-чат города, нашёл таких же энтузиастов. Улыбка до ушей — что ещё надо инженеру?!

Но с учётом того, что я живу за городом, у меня нет прямой видимости до соседних узлов других участников, то есть я не смогу отправлять и получать сообщения — по крайней мере с теми антеннами, что идут в комплекте с модулями. 

Началась эпопея с покупкой и тестированием разных антенн:

Первые PoC выглядели страшно, но очень DIY’йно:

Потом мне захотелось собрать антенну типа «Яги» самому по расчётам. Так выглядел процесс поиска точки, откуда будет связь с этой самодельной антенной:

Но потом я осознал, что чудес не бывает и прямой видимости нет. Значит что? Правильно — надо поднять антенну выше!

Поднял, закрепил на заборе — связь есть!

Счастью не было предела, когда я смог отправить сообщение в эфир и такие же сумасшедшие ребята, но уже в черте города, ответили мне. Да, да, 2025 год, Серёжа, 35 годиков, радуюсь передаче данных через радио.

Только была проблема, что так не очень удобно жить: нельзя же постоянно носить узел с собой и при необходимости вешать её на забор или столб. Если я хочу пользоваться сетью из дома, со двора, из машины, мне каждый раз придётся искать хорошую позицию для антенны.

И тут же я понял, что хочу собрать автономный узел, который в сети Meshtastic будет работать в качестве роутера. То есть у меня при себе будет маленький и простой узел с компактной антенной в роли клиента. Он будет связываться с узлом-роутером и уже через него отправлять и получать сообщения.

Ох как зачесались руки и как загорелись глаза. Возможность собрать своими руками подобную игрушку, да ещё и потратить кучу часов выходных вечеров на проектирование, подсчёты и прочее… М-м-м.

На самом деле всегда хотелось собрать своё устройство, спроектировать, подобрать корпус — а тут прям всё совпало.

Маловато метрик, или Как узел вышибло из эфира на полгода

Изучив имеющиеся платы, которые подходят для прошивки Meshtastic, я остановил свой выбор на Heltec t114. Мне понравилось заявленное малое потребление тока: около 20 мА. На деле при замерах среднее потребление у меня было даже 11 мА!

Поскольку узел должен быть автономным, я решил использовать аккумуляторы 18650. Благо у меня завалялось несколько штук с прошлых поделок. Начал с одной банки 18650. Тут большие вопросы к морозостойкости, ибо в Уфе морозы бывают и под −40 градусов. Но будем двигаться постепенно. 

Да, узел рядом с домом на заборе, но забирать и заряжать его раз в несколько суток мне лень. Тянуть туда электричество не хочется.

Решил, что пора попробовать солнечную панель.

Сидел, считал потребление, читал отзывы на панели, решил попробовать на 5 Вт. По моим подсчетам должно было хватить, ну и опять же — это ж процесс. Не получится — усовершенствуем.

Ну что ж, подключаем солнечную панель, через контроллер заряда — на наш аккумулятор, а с него подаём питание на плату Heltec. Всё работает, летом и осенью показало себя прям прекрасно.

Заряд держится хорошо — за ночь падает примерно до 20 %. После ночи аккумулятор заряжается очень шустро, учитывая, что это всего одна банка 18650.

То есть буквально за несколько часов аккумулятор с 20 % зарядился до конца.

И тут я осознал, что мне маловато метрик…

Я хочу видеть, сколько приходит с солнечной панели, сколько потребляет плата, какой заряд у АКБ. Ведь в будущем можно будет доработать устройство, опираясь на показания тока: сделать, скажем, поворотную платформу на сервоприводах, чтобы собирать максимум солнечной энергии. А может, просто поставить вторую панель.

Начал изучать, какие существуют решения. Наткнулся на модуль INA3221 — и там прям идеально под меня есть три канала.

И вот это стало поворотным моментом, который вышиб мой стационарный узел из эфира на полгода.

Начало приключений: беру в руки паяльник

Здесь я спрятал важный момент касаемо INA3221.

Есть две версии платы. Нам нужна та, где явно видны дорожки с каналов, уходящие на резисторы. И либо придётся напильником дорабатывать плату и перерезать дорожки и прочее, либо сразу взять ту, что подходит под задачу.

Неподходящая плата:

Подходящая плата:

В итоге модуль INA3221 — прям то, что нужно! Нарисовал себе следующую схему:

По задумке я смогу видеть напряжение и ток солнечной панели, АКБ и, собственно, потребление платы Heltec T114.

Дождался платы, собрал — ни черта не работает!

Начинаем погружение в недра. Всё это работает по шине I2C.

Нажмите, чтобы узнать о том, что такое I2C.

I2C — это как школьный класс, где работает чёткий порядок общения.

В роли учителя выступает главный контроллер — в нашем случае плата Heltec. Она, как и учитель, инициирует все действия: опрашивает учеников (датчики) или просит их что-то записать. 

Датчики не говорят сами по себе, а только отвечают, когда к ним обращаются. При этом все ученики синхронизированы с учителем: они подстраиваются под его темп и выполняют действия строго по его сигналу.

Простое и элегантное решение, на мой взгляд.

Каждый «ученик» — то есть каждое I2C-устройство — имеет уникальный адрес, по которому «учитель» (плата Heltec) к нему обращается. Но, как и в реальном классе, фамилии могут совпадать: разные датчики иногда используют один и тот же заводской адрес.

Поэтому очень важно, когда вы добавляете устройства в i2c-шину, заранее узнать их адрес в документации, а лучше ещё и явно его проверить через i2c-сканнер.

Получается такой процесс:

  • Учитель (Heltec T114) обращается конкретно к Иванову: «Сообщи температуру за окном».

  • Иванов отвечает: «24 градуса!» — и все в классе это слышат.

  • Но только учитель записывает ответ себе в журнал. Остальные «ученики» просто молча слушают — им эта информация не нужна, так что они её игнорируют.

Хм-м… Почитал в интернете: мол, надо в настройках узла Meshtastic указать адрес i2c-модуля — 42. И тут я потратил несколько часов, чтобы осознать, что приложение Meshtastic под iOS не обладает полным функционалом. Подключив плату к компьютеру, соединился через веб-клиент — и вот там уже нашёл нужную мне настройку, указал адрес 42… Не работает.

Пошёл опять читать, узнал, что плата работает на адресе 40 по умолчанию. Указал адрес 40 — не работает.

Нашёл в документации Meshtastic, что INA3221 слушается на 42-м адресе. А сам модуль по умолчанию отвечает на 40-м. Хм-м. Пошёл искать информацию по модулю — хвала инженерам-проектировщикам, они продумали и это. Оказывается, надо просто сделать перемычку A0-SDA и адрес станет 42. Сказано — сделано. Фото взято из интернета:

Паяльник в руки и вуаля. С полной уверенностью в победе подключаю — не работает.

Как полгода ушло на одну перемычку

Я немного расстроился и отложил разобранный узел в дальний ящик, ибо было уже не так много свободного времени. Раз в пару месяцев я возвращался, вновь читал, искал, где же я допустил ошибку, но никак не мог найти. Да и времени вечно было мало.

Каждый раз я полностью перепроходил путь: смотрел на перемычку, убирал её, добавлял другие — то есть проверял 40-й адрес (без перемычек), 41-й, 42-й, 43-й, устанавливая разные перемычки. И НИ-ЧЕ-ГО!

Плата внешне выглядела идеально, не было ничего прогоревшего. Я прозвонил мультиметром резисторы и не нашёл проблем. Но на всякий случай заказал вторую.

И вот уже в 2026 году в прекрасный свободный выходной я решил, что это не дело. Ну как так-то? Мне нужно разобраться. И я пошёл по пути, которому всегда учу своих инженеров: от простого к сложному.

У меня есть плата. Она вообще работает?

Как проверить?

Можно добыть где-нибудь осциллограф и посмотреть, меняются ли показатели при изменении вольтажа на каналах… Но это снова сложный дебаг. Надо проще! 

Для начала надо понять, а на каком адресе вещает плата? Как? Можно же собрать i2c-сканер. Если кратко, это устройство с определённой прошивкой, которое определяет, на каком адресе на шине i2c общается INA3221 (в моём случае). В вашем это может быть датчик или другое устройство на шине.

Потянулся к коробке с электроникой, но ардуинки там не нашлось. Зато нашлась старая Raspberry Pi 2. Прекрасно! Убираю перемычку, чтобы эксперимент был чистым, — фактически привёл плату к заводскому виду.

Включаю, подключаюсь по SSH на малинку, ставлю пакет i2c-tools и сканирую. 

(INA3221-Python-Library) root@raspberrypi:~/INA3221-Python-Library # i2cdetect -y 1
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- -- -- -- -- -- -- -- -- -- -- -- --
10: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
30: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
40: 40 -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
50: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
60: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
70: -- -- -- -- -- -- -- --

Адрес 0x40, супер!

Ну, думаю, дай проверю, отдаёт ли данные по адресу 0x40:

i2cdump -y 1 0x40
 ------------------------------
LIPO_Battery Bus Voltage: 0.00 V
LIPO_Battery Shunt Voltage: 0.00 mV
LIPO_Battery Load Voltage: 0.00 V
LIPO_Battery Current 1: 0.00 mA
Solar Cell Bus Voltage 2: 3.67 V
Solar Cell Shunt Voltage 2: 16.56 mV
Solar Cell Load Voltage 2: 3.69 V
Solar Cell Current 2: -165.60 mA
Output Bus Voltage 3: 3.66 V
Output Shunt Voltage 3: -16.32 mV
Output Load Voltage 3: 3.65 V
Output Current 3: -163.20 mA

Отдаёт, значит, плата рабочая.

Задумался. Что я упускаю? Где я ошибся? И вот тут я совершил роковую ошибку.

Я взял запасную плату INA3221, сделал перемычку, просканировал i2c-адреса:

(INA3221-Python-Library) root@raspberrypi:~/INA3221-Python-Library# i2cdetect -y 1
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- -- -- -- -- -- -- -- -- -- -- -- --
10: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
30: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
40: -- -- 42 -- -- -- -- -- -- -- -- -- -- -- -- --
50: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
60: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
70: -- -- -- -- -- -- -- --

В итоге получил 0x42 и впал в ступор.

Попробовал получить с неё данные на малинке:

i2cdump -y 1 0x42
------------------------------
LIPO_Battery Bus Voltage: 0.00 V
LIPO_Battery Shunt Voltage: 0.00 mV
LIPO_Battery Load Voltage: 0.00 V
LIPO_Battery Current 1: 0.00 mA
Solar Cell Bus Voltage 2: 3.67 V
Solar Cell Shunt Voltage 2: 16.68 mV
Solar Cell Load Voltage 2: 3.69 V
Solar Cell Current 2: -167.20 mA
Output Bus Voltage 3: 3.66 V
Output Shunt Voltage 3: -16.44 mV
Output Load Voltage 3: 3.65 V
Output Current 3: -164.40 mA

Да ну как так-то?! Почему на малинке всё отдаётся, а на Heltec t114 не работает?!

Может дело в узле? Взял другой — t-beam. Подключил первую плату — не работает. Думаю, что дело не в узле.

Долго сидел, долго думал. Сходил погулять с собакой. Решил пройтись с начала — последовательно.

Беру первую плату, делаю перемычку, сканирую адрес и…

(INA3221-Python-Library) root@raspberrypi:~/INA3221-Python-Library# i2cdetect -y 1
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- -- -- -- -- -- -- -- -- -- -- -- --
10: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
30: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
40: -- -- -- 43 -- -- -- -- -- -- -- -- -- -- -- --
50: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
60: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
70: -- -- -- -- -- -- -- --

Опа… Не понял, перемычку я сделал согласно документации, почему же адрес 0x43?

Ну, думаю, дай проверю, отдаёт ли данные на этом адресе:

i2cdump -y 1 0x43
 ------------------------------
LIPO_Battery Bus Voltage: 0.00 V
LIPO_Battery Shunt Voltage: 0.00 mV
LIPO_Battery Load Voltage: 0.00 V
LIPO_Battery Current 1: 0.00 mA
Solar Cell Bus Voltage 2: 3.67 V
Solar Cell Shunt Voltage 2: 16.56 mV
Solar Cell Load Voltage 2: 3.69 V
Solar Cell Current 2: -165.60 mA
Output Bus Voltage 3: 3.66 V
Output Shunt Voltage 3: -16.32 mV
Output Load Voltage 3: 3.65 V
Output Current 3: -163.20 mA

Отдаёт, значит, плата рабочая. 

Взял запасную плату INA3221, сканирую без перемычки — 0x40. Всё как положено. Делаю перемычку — получаю адрес 0x42. 

Подключаю вторую плату в схему — вуаля, всё работает. Метрики отдаются.

Тут пока не всё подключено, но самое главное, что данные пошли.

Думайте просто

В очередной раз убеждаюсь, что из-за хаоса и непоследовательности действий допускаются вот такие досадные ошибки, которые привели к тому, что полгода мой узел висел в офлайне. 

Почему на первом узле при установленной перемычке адрес 0x43? Я убрал перемычку, зачистил места пайки от флюса, убрал лишний припой, ещё раз сделал перемычку. И вуаля — адрес 0x42.

Возможно, где-то я допустил ошибку. Возможно, сам того не заметил, но задел паяльником соседние контакты и создал перемычку, которая не бросается в глаза. Возможно, повлияли ещё какие-то факторы. Но этот дебаг длиной в полгода в очередной раз напомнил мне золотое правило, которое я каждый день повторяю своим инженерам: думайте просто.

Оглядываясь назад, я понимаю, насколько всё было просто и примитивно. Но все мы люди.

Теперь надо всё собрать, подумать над термоизоляцией и подогревом АКБ. Я почти уверен, что одной банки не будет хватать, когда на улице ночью −25 градусов. Возможно, вообще рассмотреть иные виды аккумуляторов. Но это всё потом. Главное, что у меня есть метрики.

P. S. 

Читайте также в нашем блоге: