Русский
Русский
English
Статистика
Реклама

Iot разработка

Интернет вещей по-русски. Канальный уровень OpenUNB. Общие положения и адресация устройств

05.02.2021 12:22:10 | Автор: admin

Канальный уровень OpenUNB сильно отличается от всего, что мы видели. Так получилось из-за заложенной в OpenUNB возможности только односторонней передачи: от оконечного устройства к сети. Тем не менее, разработчики вложили много усилий в создание протокола канального уровня, чтобы устройства и сеть OpenUNB не потеряли простоту, энергоэффективность и безопасность. Давайте посмотрим, что у них получилось.


Так как канальный уровень OpenUNB довольно сложен, я решил разбить его на подсистемы и описывать их в отдельных статьях. Кстати, приведу список всех наших статей об OpenUNB:



Сегодняшняя будет про канальный уровень OpenUNB в общем и в частности про принцип адресации устройств OpenUNB. Сегодня за бортом останется безопасность и активация в сети OpenUNB. Хотя принцип адресации завязан на процедуры безопасности OpenUNB, я решил описать его в отдельной статье, чтобы не ввергать читателя в пучину лонгрида. По прочтении всех статей по канальному уровню, у вас сложится представление.


Канальный уровень отвечает за механизм управления доступом устройств к радиоканалу (Media Access Control, MAC) и механизм управления логической связью (Logical Link Control, LLC) между устройствами и сервером сети.


Канальный уровень определяет:


  1. механизм множественного доступа устройств к радиоканалу;
  2. механизм повторных передач пакетов;
  3. формат пакетов канального уровня и алгоритм их формирования;
  4. схему адресации устройств;
  5. процедуру активации (аутентификации и регистрации) устройств на сервере;
  6. механизм криптографической защиты передаваемых данных (шифрование, контроль целостности и подлинности).

Сегодня мы рассмотрим первые четыре пункта списка.


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


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


Формат пакета OpenUNB по уровням:


image


Как видно из рисунка выше, канальный уровень добавляет к пользовательским данным шесть байт (что, прошу заметить, очень мало). Далее сообщение канального уровня передается физическому, который добавляет преамбулу и помехоустойчивое кодирование (это описано ранее здесь и здесь).


В эти шесть байт входят адрес (DevAddr) и проверочное слово (MIC). Обе эти части имеют одинаковый размер (три байта) и простые, но тщательно отточенные разработчиками свойства.


Слово DevAddr это временный адрес устройства. В лирическом отступлении можно отметить, что мало можно найти протоколов IoT, в которые внедрена концепция временных адресов, хотя в сотовой связи она присутствует начиная со стандартов 2G. В OpenUNB временный адрес (меняется каждые 4 часа) формируется криптографически из базового ключа K0, привязанного к DevID, назначение которого имеет необыкновенную гибкость. Во-первых, DevID может не быть уникальным. Пользователь даже может назначить DevID случайным образом. Уникальность DevID придаст назначение соответствующего ему базового секретного ключа K0. Во-вторых, нет даже требований к длине DevID. Стандарт требует иметь его длину не менее 4 байт, но рекомендует длину 16 байт. В-третьих, такая гибкость приводит к возможности назначать DevID в разных сетях децентрализовано, не сверяясь друг с другом.


Если говорить точно, временный адрес DevAddr вырабатывается так:


$ DevAddr = MSB24 (ECB (Ka, 0x01 || Ne || 0^{n-32})),$


где Ne номер эпохи (время), а Ka ключ активации, который получается так:


$ Ka = CTR (K0, Na || 0^{n/2-16}, 0^k),$


где Na номер активации, а K0 базовый секретный ключ.


Процедуры ECB и CTR здесь это криптопреобразования "режим простой замены" и "режим гаммирования", соответственно. Эти процедуры определены в стандартах шифрования ГОСТ.


Таким образом, если считать криптопреобразования стойкими, а ключ K0 секретным, связь между DevID и DevAddr экономически оправданным способом установить не получится. Поэтому третья сторона не может сопоставить пакеты в эфире с конкретным устройством IoT, не зная ключ K0. Какой еще протокол IoT может похвастаться таким удивительным свойством?!


Слово MIC, проверочное слово, уникально. Оно имеет по меньшей мере две ипостаси: это имитовставка и слово контроля целостности в одном лице. За счет этого двойного назначения получается немалая экономия в объеме данных, а значит и в энергии, потребляемой устройством. Есть еще третья функция MIC, скрытая от неискушенного читателя. Это конкретизация соответствия DevAddr и DevID. Очевидно, ввиду малости длины DevAddr, это поле не будет уникальным для всех DevID, по крайней мере это не гарантируется криптопреобразованиями. Но существует связь DevAddr и MIC, которая определяется секретным ключом K0 и другими параметрами. Если говорить точно, то чудо-слово MIC получается так:


$MIC = CMAC24 (Km, P),$


где значение вектора P зависит от длины блока n и длины поля MACPayload. Пусть len
однобайтная целочисленная беззнаковая переменная, равная длине полезных данных
MACPayload в битах (переменная len может принимать значения 16 или 48), тогда:


если len = 48 и n = 64, то


$P = DevAddr || MACPayload || Nn || 0^{2n-len-48} || len;$


в остальных случаях


$P = DevAddr || MACPayload || Nn || 0^{n-len-48} || len.$


Процедура CMAC24 здесь это криптопреобразование "режим выработки имитовставки" согласно ГОСТ.


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


Про DevID

Идентификатор устройства DevID записывается в энергонезависимую память устройства, а также хранится на сервере сети. Идентификатор DevID должен иметь длину не менее 4 байт, а его формат может быть различным (например, в разных сетях может использоваться свой формат идентификаторов). Рекомендуется использовать идентификаторы DevID длиной не менее 128 бит.


Устройства, работающие в разных сетях, могут иметь одинаковые идентификаторы DevID. Таким образом, назначение идентификаторов DevID в каждой сети может осуществляться независимо. Например, если идентификаторы DevID назначают операторы сети, то им не требуется договариваться друг с другом об уникальности идентификаторов DevID для устройств из разных сетей. Рекомендуется, чтобы устройства, работающие в одной сети, имели уникальные идентификаторы DevID. Например, их может централизованно назначать оператор сети. Однако допустимо, чтобы устройства, работающие в одной сети, имели совпадающие идентификаторы DevID. Например, пользователи могут сами назначать устройствам случайные идентификаторы DevID и сообщать их на сервер сети при активации устройства. Алгоритм разрешения ситуаций, когда несколько устройств из одной или разных сетей имеют одинаковые идентификаторы DevID, представлен в стандарте.


Про DevAddr

Временный адрес устройства DevAddr имеет фиксированную длину 3 байта. Значение временного адреса устройства DevAddr изменяется в процессе работы устройства и передается в пакетах канального уровня:


  • начальное значение временного адреса DevAddr0 = CRC24 (DevID). Этот адрес передается только в служебных пакетах активации, которые отправляются при активации устройства для его аутентификации и регистрации на сервере сети;
  • для всех последующих пакетов, передающих полезные данные уровня приложений, устройство использует временный адрес DevAddr, который пересчитывается каждую эпоху (раз в EPOCH_DURATION) с помощью функции криптографического преобразования.

Важно отметить, что используемая схема вычисления временных адресов DevAddr не гарантирует их уникальность. Разрешение возможных коллизий временных адресов разных устройств осуществляется на сервере сети при расшифровании принятых пакетов на этапе проверки имитовставки MIC.


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


Как обычно, теоретическая проработка у нас сразу вытекает в практику. Исходники криптопреобразований для оконечного устройства уже можно найти на Github.


Кстати, физический уровень нами уже сделан и сейчас проходит проверку на местности. Вы уже можете взять исходники передатчика оконечного устройства и приемника базовой станции и опробовать дальность работы самостоятельно. Для этого нужно минимальное железо. Заинтересованных прошу обращаться. Мы поможем консультацией первым энтузиастам. Наш бессменный программист deef137 всегда на связи.


Пока писалась эта статья, пришла отличная новость: стандарт опубликован на сайте Сколтеха. Теперь полная картина не ускользнет от вас.

Подробнее..

Интернет вещей по-русски. Процедура активации OpenUNB

28.02.2021 12:13:00 | Автор: admin

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


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


В обычных, двусторонних системах такая информация вставляется в передаваемый информационный пакет. Грубо говоря, пакеты нумеруются. В экономичных система передачи типа Интернета вещей такой метод расточителен. В таких системах выгоднее вести счетчики времени на двух сторонах отдельно, а не передавать его в пакете. В стремлении к совершенству, так и было сделано в OpenUNB.


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


В OpenUNB активация устройства производится пользователем. Также необходим доверенный канал между пользователем и сервером сети. Схема взаимодействия представлена ниже:


image


Как видно из схемы, пользователь должен иметь некоторое мобильное устройство с программой и находиться рядом с устройством OpenUNB.


В стадии "запрос на активацию" пользователь должен по служебному каналу отправить на сервер запрос на активацию, в котором передается идентификатор DevID активируемого конечного устройства. Если активация возможна, то сервер сообщает об этом. Далее пользователь делает "запуск процедуры активации на устройстве". Это может быть пакет по радио-интерфейсу или другому, удобному. Это также может быть нажатие кнопки "активация" или просто включение питания устройства. После этого события устройство передает "служебный пакет активации", в котором содержится номер текущей активации.


Если сервер правильно (совпадает имитовставка MIC) получает сообщение обо активации от устройства по каналу OpenUNB, то он индицирует пользователю "подтверждение успешной активации". После этого пакеты данных могут передаваться защищенно.


Рассмотрим подробно процедуру со стороны устройства и со стороны сервера.


Со стороны устройства процедура выглядит так:


  1. проверяется текущее значение счетчика активаций Na. Если счетчик активаций уже достиг максимально возможного значения, то данное устройство больше не может использоваться, и выключается;
  2. увеличивается значение счетчика активаций: Na = Na + 1;
  3. вырабатывается ключ активации Ka;
  4. вырабатывается ключ расчета имитовставки Km для эпохи Ne = 0;
  5. формируется служебный пакет активации, в поле MACPayload которого содержится текущее значение счетчика активаций Na, а в качестве адреса указывается DevAddr0 = CRC24(DevID). При этом поле MACPayload передается в открытом виде (не шифруется), а поле имитовставки MIC рассчитывается на ключе Km для номера Nn = 0. Сформированный служебный пакет активации должен быть отправлен MAX_PKT_TX_NUM раз подряд для повышения вероятности его доведения;
  6. устройство считает активацию успешно завершенной и может передавать пакеты полезных данных.

Напомним формат пакета OpenUNB:
image


Сервер по приему пакета активации ищет адрес из пакета в списке адресов активированных устройств. Для каждого из найденных совпадений:


  1. сохраняется полученное значение счетчика активаций устройства Na. Если для данного устройства ранее уже осуществлялась успешная активация, то сервер должен дополнительно проверить, что текущее значение Na больше чем значение Na, полученное при предыдущей успешной активации. Если эта проверка завершается неуспешно, то сервер переходит к следующему найденному устройству;
  2. вырабатывается ключ активации Ka;
  3. вырабатывается ключ расчета имитовставки Km для эпохи Ne = 0;
  4. для пакета проверяется совпадение имитовставки MIC на ключе Km для номера Nn = 0.

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


Детали работы процедур активации OpenUNB смотрите в первоисточнике на сайте Сколтеха.


Реализованные процедуры активации и другие процедуры безопасности доступны в исходниках здесь.


Наш бессменный мастер Интернета вещей deef137 всегда на связи и готов помочь с вопросами по коду.

Подробнее..

Интернет вещей по-русски. Безопасность в OpenUNB

08.03.2021 14:16:44 | Автор: admin

В настоящее время в эпоху развитого интернета мы настолько привыкли к хорошей информационной безопасности протоколов передачи информации, что тема создания новых протоколов несколько ушла в тень. Зачем что-то еще изобретать? Просто выбери из имеющихся. Но Интернет вещей поднимает эту тему заново.


Для иллюстрации актуальности я приведу в пример протокол CRISP, кстати, отечественной разработки. Наличие такой разработки, доведенной уже до статуса методических рекомендаций Технического комитета по стандартизации "Криптографическая защита информации", подтверждает практическую непригодность обычных "тяжелых" протоколов безопасности для Интернета вещей. Они оказываются слишком ресурсоемкими.


Различных радио-протоколов Интернета вещей сейчас наплодилось огромное множество, но в сфере LPWAN не везде разработчики протокола передачи берут на себя тяжелую ношу защиты информации. Можно долго спорить, нужно ли вообще включать защиту в радио-протокол LPWAN, а не перекладывать ее на вышележащие уровни, но если предложенная схема хороша, то стоит надеяться на большую вероятность внедрения стандарта в индустрию. Главный тезис: вообще без защиты в Интернете вещей сейчас уже нельзя. И она должна быть на уровне.


Так же рассуждали и разработчики OpenUNB, ставя во главу угла энергоэффективность и встроенную безопасность информации. Тем, кто еще ничего не знает про OpenUNB, я советую прочитать предыдущие статьи на эту тему:



а также изучить первоисточник на сайте Сколтеха.


Сегодня мы рассмотрим механизм криптографической защиты передаваемых данных (шифрование, контроль целостности и подлинности).


Чтобы обеспечить базу безопасности, у каждого устройства и сервера должно быть что-то общее, секретное, которое никто не знает. В OpenUNB это секретный ключ шифрования K0, имеющий длину k, равную 128 или 256 бит. Весь остальной протокол должен быть сделан так, чтобы этот базовый, основной ключ не стал бы известен никому никаким образом, а информация при этом была защищена. Поэтому базовый ключ претерпевает такое множество преобразований в своем стремлении встретиться с информацией.


Ключ K0 используется только для формирования (порождения) рабочих ключей, которые непосредственно используются в процедуре криптографической защиты данных. (Чтобы лучше понимать последующее повествование, прочитайте статьи о канальном уровне: первую и вторую). Хотя, я думаю, специалисту по безопасности все должно быть понятно и так.


В недрах устройства и сервера OpenUNB есть счетчик активаций Na и счетчик эпох Ne, которые остаются примерно одинаковыми в процессе работы системы. Сначала вырабатывается ключ активации:


$ Ka = CTR (K0, Na || 0^{n/2-16}, 0^k).$


Потом уже по ключу активации вырабатываются рабочие ключ шифрования Km и ключ имитозащиты Ke:


$ Km = CTR (Ka, 0x02 || Ne || 0^{n/2-32}, 0^k),$


$ Ke = CTR (Ka, 0x03 || Ne || 0^{n/2-32}, 0^k).$


Для криптографических преобразований разработчики OpenUNB рекомендуется использовать блочный шифр Магма, который имеет длину блока n = 64 бита и длину ключа k = 256 бит, определенный в стандарте ГОСТ Р 34.12-2015.


Шифрование выглядит так:


$ EncryptedMACPayload = CTR (Ke, Nn || 0^{n/2-16}, MACPayload),$


где Nn номер пакета, а выработка имитовставки так:


$MIC = CMAC24 (Km, P),$


где значение вектора P зависит от длины блока n и длины поля MACPayload. Пусть len
однобайтная целочисленная беззнаковая переменная, равная длине полезных данных
MACPayload в битах (переменная len может принимать значения 16 или 48), тогда:


если len = 48 и n = 64, то


$P = DevAddr || MACPayload || Nn || 0^{2n-len-48} || len;$


в остальных случаях


$P = DevAddr || MACPayload || Nn || 0^{n-len-48} || len.$


Процедура CMAC24 здесь это криптопреобразование "режим выработки имитовставки" согласно ГОСТ.


Далее эти поля вставляются на свои места. Напомним схему формирования пакета:
image


Более подробно, со всеми деталями, вы можете прочитать о безопасности в OpenUNB в первоисточнике.


Как мы видим, разработчики постарались сделать энергоэффективность и защиту в OpenUNB бескомпромиссной. Тем не менее, одной из целей моих публикаций является привлечение специалистов к внимательному рассмотрению OpenUNB и к конструктивной критике протокола.


Как всегда, исходники крипто-преобразований от deef137 доступны на Github.

Подробнее..

Микроволновка, знающая о тебе всё что такое Интернет вещей (IoT)?

04.09.2020 14:06:16 | Автор: admin
С появлением на рынке стиральных машин, духовок, дверных замков и даже ваз с подключением к интернету, Bluetooth- или Wi-Fi-модулем в борьбу за интернет-потребителя включились не только разработчики ПО, но и промышленные дизайнеры. Так явление интернет вещей (Internet of Things) стал неотъемлемой частью нашей жизни.

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

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

image

При совмещении данных из различных источников формируется практически бесконечный информационный поток, который будет полезен для разных сфер, начиная от медицины и науки, заканчивая логистикой транспорта и добычей полезных ископаемых.

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

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

Хорошим примером такого использования информации являются различные фитнес приложения, такие как Google Fit. Они обрабатывают информацию с фитнес-трекеров, смарт-браслетов, умных часов и составляют общую картину состояния здоровья, физических нагрузок, а также возможных проблем с сердцебиением, уровнем сахара и температурой тела. Если добавить к этому онлайн-платформу для медиков и больниц, получается сверхплатформа по управлению качеством жизни сотен тысяч людей.

image

Но есть и белые пятна в этом идеальном мире интернета вещей. Трудность состоит в том, как грамотно совместить разные платформы и устройства от разных поставщиков и при этом избежать риска утечки информации и их несанкционированного использования. Уже сейчас разрабатываются такие гибридные инструменты для работы на различных устройствах и платформах: Samsung SmartThings и Apple HomeKit для решений по смарт-домам; Dash и Mojio для интеллектуального управления машинами; Validic и Jawbone UP для контроля состояния здоровья.

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

В свою очередь, взаимодействие разработчиков с потребителями породило таких гигантов, как Instagram, WeChat, Uber и даже Angry Birds. Многомиллиардные бизнесы возникли из пожеланий потребителей, а не из идеи разработчиков. Таким образом, каждый может сделать вклад в то приложение, которым будет пользоваться. Это и есть основной стимул для роста интернета вещей.

Для создания продукта разработчики открывают доступ пользователям и потенциальным покупателям, чтобы предлагать, разрабатывать и использовать новые идеи для уже работающих платформ. Одними из таких платформ являются Apple CarPlay и Google Android Auto, которые дают доступ производителям автомобилей к своим технологиям.

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

Путь одной команды от велосипедов до IoT-платформы

28.10.2020 20:04:59 | Автор: admin
Привет, Хабр!
Мы, команда Rightech, наконец-то решили начать вести блог. У нас накопилось много опыта в построении высоконагруженных IoT-систем, и мы решили, что просто обязаны им делиться! Совсем недавно прошел запуск публичной версии нашей платформы RIC (Rightech IoT Cloud), и теперь ей может воспользоваться каждый желающий. Но сначала расскажем, кто мы и откуда появились.

C чего всё начиналось


В далеком 2011 году мы скорее были командой фрилансеров из города Орел и начинали с того, что программировали ряд аппаратных разработок, связанных с реализацией систем автоматизированных измерений и управления. Подключали сенсоры и актуаторы к микроконтроллерам, реализовывали протоколы обмена, первичную обработку данных и автоматизацию.

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

Наши заказчики искренне не понимали, почему они не могут смотреть/тестировать промежуточный результат. Почему он выглядит как бегущие строки в консоли, а для управления актуатором нужно не нажать на тачскрин, а отправить Modbus команду. К программированию интерфейсов мы приступали в тот момент, когда было уже готово API и проработана автоматизация.

На тот период времени наш рабочий процесс представлял собой следующую последовательность:

  1. физически подключить компоненты системы в одну сеть;
  2. реализовать протоколы обмена данными;
  3. реализовать обработку данных (фильтрация, применение функций преобразования, проведение косвенных измерений и т.д.);
  4. преобразовать данные в высокоуровневые структуры;
  5. описать конечные автоматы системы;
  6. реализовать API для вывода данных в интерфейс и запуска автоматов;
  7. реализовать интерфейс системы (тачскрин/нативное приложение/интеграция во внутренние системы заказчика).

И, как вы понимаете, из проекта в проект до последнего этапа заказчик с трудом понимал, что мы делаем, и это всегда было почвой для недоверия и конфликтов. Конечно, когда мы сдавали работу, заказчик был рад и доволен, но потраченные нервы и ощущение того, что мы по сути пилили на 90% очередной велосипед на новом стеке, оставалось.



В результате мы приняли решение создать универсальный фреймворк. На наше решение повлияли и интересы заказчиков. Управленцы и владельцы бизнеса, как правило, заинтересованы в создании конечных пользовательских кейсов и часто не углубляются в механизм работы системы. Для успешного выполнения поставленных ими задач нам требовалось больше фокусироваться на разработке пользовательских сценариев и интерфейсов, так как именно они несут в себе основную коммерческую ценность создаваемого решения. При этом 90% затрат на разработку сосредоточено во внутренних, невидимых конечному пользователю системах проекта.



Первоначальная идея платформы RIC трансформировалась и изменялась вместе с рынком, находила все больше областей применения. Разработанный нами за 4 года фреймворк позволял сосредоточиться на процессах создания ценности решения, воплощения задуманной бизнес-логики и продвижения конечного продукта на рынок. RIC был полностью готов в 2016 году, оставалось только создать компанию и найти деньги

Rightech. История создания


У нас совершенно отсутствовал опыт в привлечении денег. Однако в 2016 году нам удалось привлечь первые инвестиции от фонда, вложившегося в компанию Делимобиль. На эти деньги мы создали компанию Rightech, которая стала домом для нашего проекта. А первым действительно крупным внедрением нашей технологии, как вы уже догадались, стал каршеринг Делимобиль. Сразу оговорюсь, что приложения и CRM систему разрабатывали не мы, но тысячи автомобилей и терабайты машинногенеренных данных стали достойной проверкой, которую RIC уверенно прошел.

Помимо шерингов, к 2019 году мы успели автоматизировать Digital Out Of Home рекламу, построить сбор данных с газотурбинных генераторов электроэнергии и многое другое. Команда занималась не только рыночными внедрениями, но и развивала RIC в целом: реализовали множество транспортных протоколов, оптимизировали серверную инфраструктуру и расширили систему автоматизации.

Как и следовало ожидать, нам стало тесно в рамках Делимобиль и мы начали развивать платформу в сторону публичного облака. К этому времени цели инвестирования со стороны фонда были достигнуты, и в начале 2019 года мы выкупили его долю. Это позволило команде проекта сконцентрироваться на реализации по-настоящему массовой технологии.

Подробнее о платформе


Так что же такое IoT-платформа? Во что превратился наш фреймворк заменитель велосипедов RIC?

Любой IoT проект состоит из следующих принципиальных компонентов или слоев:

  • устройства умные устройства, датчики и актуаторы, на основе которых осуществляется сбор данных и автоматизация;
  • сети передачи данных по ним происходит передача данных и команд между компонентами IoT системы;
  • платформа инфраструктура, обеспечивающая интероперабельность (способность к взаимодействию) компонентов системы, обработку данных и передачу ее в прочие системы;
  • приложения представляет собой конечную цель IoT-проекта, на этом уровне работают конечные пользователи и на нем же, по сути, создается ценность всей системы.



Rightech IoT Cloud (или RIC) это облачная платформа Интернета Вещей, выступающая в качестве промежуточного программного обеспечения (middleware) при разработке IoT-решения. RIC включает в себя все необходимые программные элементы, позволяющие инженерам любого уровня создавать приложения с использованием любых IoT-устройств без необходимости создавать соответствующую программно-аппаратную инфраструктуру. Да-да, именно любых устройств. Мы выложили не все реализованные протоколы в публичную версию RIC. Если вы не нашли протокол своего устройства, можете нам написать и мы его обязательно добавим в публичную версию.

Небольшой лайфхак: иногда не стоит выводить всю логику на сторону платформы. Какие-то важные процессы можно оставить на стороне железа на тот случай, если пропадет интернет. Или сценарии, в которых важно реальное время, например, две команды должны быть выполнены в строгом интервале между ними. Тогда запуск этого сценария можно сделать через RIC, а логику исполнения оставить на устройстве.

В отличие от существующих аналогов платформа Rightech не требует написания кода, кроме относящегося к созданию Приложений, являющихся целью IoT-проекта. Интеграция платформы с уровнем приложений происходит посредством высокоуровневого REST API, и производится не сложнее, чем интеграция Google карт.



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

Публичное облако


Весной мы запустили регистрацию на наше публичное облако, и теперь каждый пользователь может бесплатно подключить до 10 устройств и спрототипировать свой будущий бизнес или же автоматизировать, например, теплицу или дом. Любой IoT проект может взять всё необходимое в платформе RIC и реализовать свою уникальную систему обработки и представления получаемых данных практически без программирования тех самых 90% айсберга.

Наш короткий рассказ подошел к концу. Надеемся, что мы вам понравились, и в свою очередь обещаем делиться своим опытом и актуальной информацией в сфере IoT.
Кстати, мы есть и в Телеграм с чатом единомышленников.
Just do IoT!

Полезные ссылки:


Обучающие видеоролики на примере мини-кейсов
Создайте свой IoT-проект уже сейчас
Присоединяйтесь к единомышленникам
Подробнее..

Анонсируем новую версию Rightech IoT Cloud v2.2. Небольшой обзор

04.12.2020 16:09:39 | Автор: admin
Всем привет!

В рамках нашего блога мы планируем делиться не только историями и опытом, но также освещать последние нововведения и изменения, связанные с платформой Rightech IoT Cloud (RIC).
Недавно мы опубликовали версию RIC v2.2. А теперь рассказываем, что же именно вошло в релиз этого квартала.

Ну что, погнали?

Опираясь на отзывы и предложения наших пользователей, мы решили добавить следующие функции:

  • Import/export сущностей платформы, а именно моделей, объектов и автоматов.
  • Обработку ошибок в редакторе автоматов.
  • RIC-app упрощенную мобильную версию платформы.

image

Предисловие


Если вы новый пользователей нашей платформы, то наверное, многие из перечисленных параметров выше вам непонятны. Давайте немного разберем, что есть что.

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

Объект является представлением устройства, над которым осуществляется контроль и управление посредством использования функций платформы.

Автомат это сценарий автоматизации, позволяющий выстраивать логику поведения вашего устройства.

Более подробно ознакомиться со всеми параметрами платформы можно в нашей документации.

Вернемся к обновлениям

Import/export сущностей платформы


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

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

Модели

Возможность импорта/экспорта моделей особенно помогает при передаче своей реализации задачи другому человеку. Очень удобно поделиться программным кодом в виде, например, скетча Arduino и моделью объекта в виде JSON-файла.

Экспорт модели:

image

Импорт модели из файла:

image

Импорт модели по ссылке:

image

Объекты

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

Экспорт объекта:

image

Импорт объекта из файла:

image

Импорт объекта по ссылке:

image

Автоматы

Также появилась возможность поделиться своими сценариями и использовать автоматы других пользователей. Изучайте опыт других пользователей. Делитесь своими достижениями. Спрашивайте совета и не бойтесь критики. Мы также будем выкладывать собственные проекты на github например, те решения, которые уже используются в нашем офисе и в повседневной жизни наших сотрудников.

Экспорт автомата:

image

Импорт автомата из файла:

image

Импорт автомата по ссылке:

image

Обработка ошибок в редакторе автоматов


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

Автомат с ошибками может быть сохранен и запущен, но в этом случае нет гарантии корректного исполнения автомата, поэтому советуем обращать внимание на логи запущенного автомата.

Именно поэтому мы добавили в интерфейс создания и редактирования автоматов дополнительную информацию о возникающих ошибках.

Автомат с ошибками:

image

Состояния

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

Ошибки в состоянии:

image

Переходы

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

Возможно несколько вариантов ошибок:

  • Отсутствие события, которое вызывает переход между состояниями;
  • Отсутствие параметра, который используется в условии перехода.


Ошибки в переходах:

image

Ric-app


Рады сообщить, что у нас появилась мобильная версия. Приложение обладает основными возможностями платформы, связанными с контролем в режиме реального времени состояния объекта и его местоположения, управлять объектами посредством отправки команд, следить за оповещениями платформы.

Приложение для Android доступно в Play Market по ссылке. Приложение для iOS в скором времени появится в App Store.

Объекты

В списке объектов видна информация о статусе объектов. Можно зайти в каждый объект, посмотреть все его параметры, историю пакетов. Кроме того, доступна возможность отправки команд на устройства.

Список объектов:

image

Состояние объекта:

image

История объекта:

image

Управление объектом:
image

Карта

Меню с картой аналогично карте в интерфейсе платформы.

Карта:

image

Оповещения

Сообщения, генерируемые в автоматах, также видны в мобильном приложении в меню с сообщениями.

Оповещения:

image

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

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

Stay tuned & just do IoT!

Полезные ссылки:


Обучающие видеоролики на примере мини-кейсов rightech.io/video-tutorials
Создайте свой IoT-проект уже сейчас dev.rightech.io/signup
Присоединяйтесь к единомышленникам t.me/rightech_iot
GitHub github.com/Rightech/ric-public
Вопросы и предложения development@rightech.io
Подробнее..

Интернет вещей по-русски. Помехоустойчивое кодирование в OpenUNB

16.12.2020 00:12:34 | Автор: admin

Доступ к среде (MAC, Media Access Control) в OpenUNB очень прост случаен и асинхронен. Этот вид доступа еще называют асинхронная ALOHA. Даже WiFi может похвастаться более сложным вариантом MAC. За счет этого упрощения оконечные устройства OpenUNB могут сильно экономить в потребляемой энергии и стоимости оборудования. Но такой способ доступа к среде приводит к ошибкам при передаче, которые чаще происходят группами. Поэтому, хотя и не только поэтому, помехоустойчивому кодированию в OpenUNB уделено достаточно много внимания.


В настоящее время примером качественно спроектированных систем радиосвязи являются стандарты сотовой связи. Этот факт доказывается колоссальным прогрессом в способах передачи информации по радио, изменившим всю нашу жизнь. Детали реализации стандартов сотовой связи даже используются в профильных университетах, как условия задач. Создатели OpenUNB также не стали изобретать чего-то нового в смысле помехоустойчивого кодирования, а взяли пример со стандарта Интернета вещей от 3GPP NB-IoT. Там при передаче в сторону базовой станции применяется полярное кодирование.


К слову, на Хабре есть отличные статьи по помехоустойчивому кодированию вообще и по кодированию LDPC в частности. Тем, кто путается в терминах и базовых понятиях, будет полезно их прочитать.


В настоящее время особую популярность набирает новый вид помехоустойчивых кодов, называемых полярными кодами. Как было доказано в [1], предложенные Ариканом полярные коды способны асимптотически достигать границы Шенона. Данное преимущество позволяет использовать полярные коды в современных телекоммуникационных системах мобильной связи. За довольно короткое время развития полярных кодов было предложено множество алгоритмов декодирования. Идея традиционного алгоритма декодирования [1] для полярных кодов заключается в последовательной оценке информационных бит. Таким образом, если на каком то шаге декодирования происходит ошибка, то и оценка всех остальных бит тоже будет ошибочной. Такой алгоритм декодирования известен, как алгоритм последовательного исключения (ПИ). Одним из способов преодоления зависимости от оценок предшествующих бит является использование списочного алгоритма Тала-Варди.


В настоящей статье рассматривается списочный алгоритм Тала Варди, предложенный в [2] для декодирования полярных кодов, который существенно уменьшает вероятность ошибки декодирование и позволяет реализовать декодирование почти по максимуму правдоподобия уже для небольшого размера списка (L = 16).


Основная идея, лежащая в основе алгоритмов кодирования и декодирования полярных кодов поляризация канала. Поляризацией канала является операция преобразования канала связи в N независимых его копий, в которых вероятность ошибки при передаче данных стремится к 0, или к 1. Каналы с единичной вероятностью ошибки будем называть замороженными. Таким образом появляется возможность эффективного использования канала связи и передачу сообщений через множество каналов, обладающих низкой вероятностью ошибки. Полярные коды строятся на основе использования матрицы вида:


$G = \begin{pmatrix} \ 1& \ 0 \\ \ 1& \ 1 \end{pmatrix}^{\otimes m} $


Матрица G называют ядром Арикана, а через m обозначают ее кронекеровскую степень. Формально алгоритм кодирования полярного кода состоит из двух основных этапов, а именно: формирования кодовой последовательности и умножения на матрицу Арикана. Под формированием кодового слова понимается вставка информационных бит в незамороженные позиции кодовой последовательности, и дальнейшее умножение этой последовательности на матрицу Арикана. Степень матрицы соотносится с длинной кодовой последовательности как N = 2^m.


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


Для начала давайте проверим идею, что полярные коды действительно так хороши для нашего случая. Для этого сравним их с обычными конкурентами: БЧХ, Рида-Соломона, Голея. (Здесь следует заметить, что полярный код чувствителен к виду модуляции и что он особенно хорош именно при DBPSK.) Проведем имитационное моделирование в Matlab вероятности битовой ошибки в зависимости от отношения сигнал-шум на бит (ОСШб) указанных кодов с примерно одинаковыми скоростями. Результаты моделирования приведены на рисунке. По графикам видно, что даже в области малых значений ОСШб полярный код немного, но лидирует.


image


Выигрыш в 1 дБ или меньше может показаться мелочью, не достойной усилий. Но подумайте о радиоинженере, которому вы предложите уменьшить коэффициент шума уже вылизанного до предела приемника на 1 дБ, чтобы догнать конкурентов. Или подумайте о создателе сети IoT, которому нужно будет ставить базовые станции на 10 процентов чаще, чем конкурентам.


Следует отметить, что при более больших ОСШб разрыв полярного кода от конкурентов увеличивается. При ОСШб около 7.5 дБ вероятности ошибок уже отличаются на порядок, что будет приводить к значительно меньшим потерям пакетов.


Перейдем в практическую плоскость. Кодер полярного кода реализован в микроконтроллере, исходники здесь. В OpenUNB есть два варианта размера информационного блока: 64 и 96. Согласно алгоритму кодирования полярным кодом, необходимо сформировать промежуточную кодовую последовательность, которая будет содержать биты информационного блока в известных информационных позициях, а биты во всех замороженных позициях будут равны нулю. Код алгоритма представлен ниже:


int n_polar = _frozen_indicator.size();std::vector<uint8_t> iwd_s(n_polar);std::vector<int> inf_idx;std::vector<uint8_t> u(n_polar);for (int i = 0, j = 0; i < iwd_s.size(); i++) {    if (_frozen_indicator[i] == 0) {        iwd_s[i] = _iwd[j++];        inf_idx.push_back(i + 1);    }    else {        iwd_s[i] = 0;    }    u[i] = 0;}

Результатом работы данного алгоритма является промежуточное кодовая последовательность размером 128 или 196 бит, соответственно. Далее для того, что бы умножить промежуточную кодовую последовательность на матрицу Арикана, необходимо дополнить промежуточную кодовую последовательность нуля до целой степени двойки. Умножение на матрицу Арикана осуществляется с помощью функции, приведенной ниже:


return solve_recursively_prep(inf_idx, u, iwd_s, n_polar);

Декодер реализован в приложении на Raspberry. Декодер получает от демодулятора DBSPK мягкие решения и реализует алгоритм декодирования Тала Варди.


Основная идея списочного алгоритма декодирования состоит в том, чтобы обрабатывать сразу блок из не более чем L символов за одну итерацию алгоритма. То есть задача декодирования сводится к построению кодового дерева, где на каждой итерации вычисляется значение метрики пути, и строится не более чем L наиболее вероятных продолжений этого пути. В качестве примера приведем кодовое дерево (4,3), где 3 число информационных бит.


К


На рисунке, приведенном выше, сплошными линиями обозначены наиболее вероятные пути, причем количество этих путей определяется размером списка L.


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


Декодер:


std::vector<std::vector<float>> prob;std::vector<std::vector<uint8_t>> dec = pcscl_prep(8, 16, llr, &prob, info_bit_pattern_96);dec = polar_transform_noperm(dec);dec = extract_with_filter(dec, crc_mask_96, num_of_nonzero_bits_96 - short_96);std::vector<uint8_t> crc_err;crc_err = crc_ok_array(0x327, dec);

Чтобы проверить соответствие реализации полярного кода идее, проводим натурное моделирование. Для этого создаем на столе такой стенд: подключаем RTL-SDR к Raspberry, включаем запись с эфира, запускаем передатчик и через аттенюатор записываем сигнал в файл. В софте читаем сигнал из файла, делаем измерение ОСШ и подмешивание к принимаемому сигналу шума. Далее запускаем процесс сбора статистики и уходим спать. По приходу мы имеем в распоряжении такой график:


image


График с точностью до погрешностей совпадает с графиком из модели в Matlab.


Попутно получаем график вероятности потери пакета в зависимости от ОСШ:


image.


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


P.S.


Хочется выразить благодарность нашему бессменному программисту deef137 и примкнувшему в нам специалисту по помехоустойчивому кодированию RadioTech34.


[1] Arikan E. Channel polarization: A method for constructing capacity achieving codes for symmetric binary-input memoryless channels // IEEE Transactions on Information Theory. 2009. July. Vol.55, no. 7. P. 30513073.
[2] Tal I., Vardy A. List decoding of polar codes // Proceedings of IEEE International Symposium on Information Theory. 2011. P. 15.

Подробнее..

IoT-елочка, гори!..

26.12.2020 22:16:10 | Автор: admin
Пришел новый русский в магазин, чтобы сдать новогоднюю гирлянду.
Не работает? спрашивает его продавец.
Почему? Очень даже работает, отвечает тот.
А в чем тогда дело?
Покупатель вздохнул и ответил:
Не радует.


Привет, друзья!

Очень надеемся, что гирлянда, изготовление которой мы опишем в статье, порадует вас и своим видом, и тем фактом, что вы можете ее сделать сами. Совсем не претендуя на то, что эта гирлянда станет серьезным конкурентом недорогих китайских вариантов, мы все же считаем, что такой небольшой DIY в преддверии новогоднего праздника может стать прекрасным развлечением для всей семьи, ведь тут и сборка железочек, и программирование, и составление сценария логики работы гирлянды, и, в конечном счете, созидание красоты, сделанной собственной руками!

Под катом:
  1. Собираем прототип гирлянды
  2. Пишем код для нескольких режимов работы
  3. Подключаем к платформе Rightech IoT Cloud
  4. Придумываем и реализовываем сценарий работы гирлянды
  5. Создаем праздничное настроение


image



Идея сделать гирлянду возникла не случайно. Украшая офис, мы нашли в мешке маленькую елочку, которой совершенно не холодно в офисе зимой, но совсем одиноко без огоньков, тем более что основной елке в офисе достались и игрушки, и гирлянды, а маленькой ничего. Но мы посчитали, что это не беда, а даже ее преимущество. Значит сделаем для нее не только уникальную гирлянду своими руками, но и сами выберем ей цвета светодиодов (возьмем цвета нашей компании: белый и голубой) и даже организуем ей беспроводное управление режимами по Zigbee-кнопке. А для гарантии безопасности еще и добавим автоматическое выключение по расписанию.

Модели устройств, файлы со сценариями автоматов, код для NodeMCU в конце статьи (не пытайтесь повторить это дома попробуйте повторить это дома!).

image

Собираем прототип


Создание прототипов это процесс сборки простой рабочей модели продукта или системы. Для начала построим его на макетной плате, а затем, как водится, красиво спаяем.

Итак, для маленькой гирлянды нам понадобится:

  • 12 белых и 6 голубых светодиодов, управление которыми производится независимо (назначение: гореть и радовать)
  • 2 резистора на 220 Ом, подбираемые исходя из расчета сопротивления и мощности по закону Ома (назначение: защита светодиодов от перегрева и выхода из строя)
  • 2 биполярных NPN транзистора (назначение: управляем транзистором маленьким током от управляющего пина, а пропускаем на диоды большой ток с выхода 3.3 В, так мы защищаем управляющий пин платы)
  • 2 резистора на 1 кОм на базу транзистора (назначение аналогичное, ограничиваем ток)
  • плата NodeMCU (назначение: подключение к IoT-платформе и управление транзисторами)
  • батарейки или блок питания (назначение: источник питания для платы)

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

Если изобразить на схеме, то это выглядит так:

image

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




Пишем код


Ниже представлен код для управления режимами гирлянды. Его функции:

1) установить Wi-Fi соединение и подключиться к платформе;

2) подписаться на команды сообщения с топиками led_on, led_off, led_attenuation, led_flashing и выполнять соответствующие действия по управлению светодиодами.

Команды led_on и led_off включают и выключают гирлянду, а команды led_attenuation и led_flashing задают режимы плавного горения и быстрого мигания с периодом, указанным в payload команды.

Обратите внимание, в коде мы используем библиотека Sheduler, которая нужна для того, чтобы одновременно запускать несколько потоков с задачами. Если этого не сделать, то при запуске бесконечного цикла горения светодиодов параллельно получать команды с платформы уже не получится.

#include "Arduino.h"#include "Scheduler.h"      /* https://github.com/nrwiersma/ESP8266Scheduler */#include "EspMQTTClient.h"  /* https://github.com/plapointe6/EspMQTTClient */                           /* https://github.com/knolleary/pubsubclient */// Даем разумные имена для пинов, управляемых светодиодами#define BLUE_LED_PIN 12#define WHITE_LED_PIN 13EspMQTTClient client( "<wifi-ssid>", "<wifi-password>" "dev.rightech.io", "<ric-mqtt-client-id>");// Задача для обработки поступающих командclass ClientTask : public Task { public:   void loop() {     client.loop();   }} client_task;// Задача для включения светодиодовclass LedOnTask : public Task { protected:   void loop()   {     digitalWrite(WHITE_LED_PIN, HIGH);     digitalWrite(BLUE_LED_PIN, HIGH);     shouldRunValue = false; // останавливаем этот цикл сразу после включения   }   bool shouldRun()   {     return shouldRunValue;   } public:   bool shouldRunValue = false;} led_on_task;// Задача для выключения светодиодовclass LedOffTask : public Task { protected:   void loop()   {     digitalWrite(WHITE_LED_PIN, LOW);     digitalWrite(BLUE_LED_PIN, LOW);     shouldRunValue = false; // останавливаем этот цикл сразу после выключения   }   bool shouldRun()   {     return shouldRunValue;   } public:   bool shouldRunValue = false;} led_off_task;// Задача для плавного горения светодиодов в противофазеclass LedAttenuationTask : public Task { protected:   void loop()   {     // Вычисляем задержку на один проход цикла в зависимости от полученного в payload значения     float delayValue = period.toInt() * 1000 /*в миллисекунды*/ / 2 /*на два цикла*/ / 1024 /*на каждую итерацию в цикле*/;     for (int i = 0; i <= 1023; i++) {       analogWrite(WHITE_LED_PIN, i); // горит ярче       analogWrite(BLUE_LED_PIN, 1023 - i); // тускнеет       delay(delayValue);     }     for (int i = 1023; i >= 0; i--) {       analogWrite(WHITE_LED_PIN, i); // тускнеет       analogWrite(BLUE_LED_PIN, 1023 - i); // горит ярче       delay(delayValue);     }   }   bool shouldRun()   {     updateDelayTimer();     if (isDelayed()) return false;     if (!run_group_active) return false;     return shouldRunValue;   } public:   bool shouldRunValue = false;   String period;} led_attenuation_task;// Задача для быстрого мигания светодиодов в противофазеclass LedFlashingTask : public Task { protected:   void loop()   {     float delayValue = period.toInt() * 1000 /*в миллисекунды*/;     digitalWrite(WHITE_LED_PIN, HIGH);     digitalWrite(BLUE_LED_PIN, LOW);     delay(delayValue);     digitalWrite(WHITE_LED_PIN, LOW);     digitalWrite(BLUE_LED_PIN, HIGH);     delay(delayValue);   }   bool shouldRun()   {     updateDelayTimer();     if (isDelayed()) return false;     if (!run_group_active) return false;     return shouldRunValue;   } public:   bool shouldRunValue = false;   String period;} led_flashing_task;void setup() { // Настраиваем пины в режим выхода, т.е. в режим источника напряжения pinMode(WHITE_LED_PIN, OUTPUT); pinMode(BLUE_LED_PIN, OUTPUT); // Библиотека Scheduler позволяет при необходимости запустить несколько потоков Scheduler.start(&led_on_task); Scheduler.start(&led_off_task); Scheduler.start(&led_attenuation_task); Scheduler.start(&led_flashing_task); Scheduler.start(&client_task); Scheduler.begin();}void onConnectionEstablished() { // Подписываемся на команды и запускаем нужный поток путем изменения переменной shouldRunValue client.subscribe("led_on", [] (const String & payload)  {   client.publish("base/state/light", "on");   led_off_task.shouldRunValue = false;   led_attenuation_task.shouldRunValue = false;   led_flashing_task.shouldRunValue = false;   led_on_task.shouldRunValue = true; }); client.subscribe("led_off", [] (const String & payload)  {   client.publish("base/state/light", "off");   led_on_task.shouldRunValue = false;   led_attenuation_task.shouldRunValue = false;   led_flashing_task.shouldRunValue = false;   led_off_task.shouldRunValue = true; }); client.subscribe("led_attenuation", [] (const String & payload)  {   client.publish("base/state/light", "attenuation " + payload + " sec");   led_on_task.shouldRunValue = false;   led_off_task.shouldRunValue = false;   led_flashing_task.shouldRunValue = false;   led_attenuation_task.period = payload;   led_attenuation_task.shouldRunValue = true; }); client.subscribe("led_flashing", [] (const String & payload)  {   client.publish("base/state/light", "flashing " + payload + " sec");   led_on_task.shouldRunValue = false;   led_off_task.shouldRunValue = false;   led_attenuation_task.shouldRunValue = false;   led_flashing_task.period = payload;   led_flashing_task.shouldRunValue = true; });}void loop() {}


Подключаем к платформе Rightech IoT Cloud


Подключение гирлянды:


1) Создаем модель




2) Создаем объект с этой моделью




Подключение кнопки:


1) Создаем модель




2) Создаем объект с этой моделью




Подробнее о том, как подключать ZigBee устройства, можно посмотреть в видеоуроке и почитать в статье.

Разрабатываем сценарий работы


От сценария автоматизации мы хотим следующей логики:

1) один клик (single) режим постоянного свечения и выключения;

2) два клика (double) режим плавного свечения;

3) три клика (triple) режим мигания;

4) после 20:00 автоматическое выключение гирлянды (здесь также можно использовать не просто расписание, а данные еще из одного объекта СКУДа, который собирает информацию о том, есть ли люди в офисе. Если вам интересен материал по такой теме, дайте обратную связь в комментариях ).

Готовый автомат




Давайте вкратце разберем, что тут происходит и зачем:
  1. Первым делом при старте автомата запускаем планировщик, который выключит гирлянду по расписанию, обезопасив нас от забывчивости. Запустили и забыли, он будет срабатывать каждый день автоматически.
  2. В следующем состоянии не делаем ничего, просто ждем нажатия кнопки. В это состояние мы возвращаемся каждый раз после отработки определенного режима гирлянды. Из него есть переход по событию получения данных и срабатыванию планировщика.
  3. Если получили какой-то пакет от кнопки, то переходим в состояние Получен пакет, из которого по таймеру и типу клика переходим в соответствующие режимы. Вы можете спросить, зачем тут таймер. А причина в том, что кнопка работает довольно интересненько. При нажатии три раза, она сначала присылает пакет с double, а сразу за ним triple. Такой нюанс мы и обходим таймером, иначе срабатывало бы по неактуальному клику.
  4. Также есть промежуточное состояние для одинарного клика. Как мы помним, вкл/выкл у нас работают по одному и тому же событию. Поэтому, если гирлянда не выключена (находится в любом из режимов активной работы), то мы ее выключаем, а если выключена, то включаем.

Запускаем автомат на наших объектах, проверяем фуууух, работает! Время паять!




Собираем готовое устройство


Самый простой вариант пайки гирлянды это один за другим спаивать светодиоды, предварительно надевая термоусадку. Примерно вот так:

image

Но можно пойти немного другим путем сделать не просто гирлянду, которой мы обвяжем елку, облачив ее дополнительно во все эти провода. Вместо этого на каждую веточку посадим по светодиоду (в цветочках это смотрится особенно чудесно, см. итоговое фото), стянем провода по стеблю вниз и спаяем, спрятав всю электронику в горшочке. На выходе остается только разъем под кабель питания. Ювелирно, аккуратно и очень симпатично получается. Судите сами.

image

термоусадку нагреваем паяльным феном

image

помещаем провод перед пайкой в канифоль (в таком случае не образуется тонкой оксидной пленки на поверхности провода, в результате спайка проходит легче и получается надежнее)

image

и лудим (наносим небольшой слой припоя)

image

проводок готов воссоединяться со светодиодом

image

соединяем (паяем поверхности, на которых уже есть припой)

image

фиксируем на веточке, сгибая ножки (необходимо предварительно оставить не менее 10 мм) светодиода

image

на данном этапе проводим последнее тестирование

image

готово!





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

С наступающим праздником!

Материалы к статье


image
Подробнее..

IoT-елочка, гори!.

27.12.2020 00:14:52 | Автор: admin
Пришел новый русский в магазин, чтобы сдать новогоднюю гирлянду.
Не работает? спрашивает его продавец.
Почему? Очень даже работает, отвечает тот.
А в чем тогда дело?
Покупатель вздохнул и ответил:
Не радует.

Привет, друзья!

Очень надеемся, что гирлянда, изготовление которой мы опишем в статье, порадует вас и своим видом, и тем фактом, что вы можете ее сделать сами. Совсем не претендуя на то, что эта гирлянда станет серьезным конкурентом недорогих китайских вариантов, мы все же считаем, что такой небольшой DIY в преддверии новогоднего праздника может стать прекрасным развлечением для всей семьи, ведь тут и сборка железочек, и программирование, и составление сценария логики работы гирлянды, и, в конечном счете, созидание красоты, сделанной собственной руками!

Под катом:

  1. Собираем прототип гирлянды
  2. Пишем код для нескольких режимов работы
  3. Подключаем к платформе Rightech IoT Cloud
  4. Придумываем и реализовываем сценарий работы гирлянды
  5. Создаем праздничное настроение

image

Идея сделать гирлянду возникла не случайно. Украшая офис, мы нашли в мешке маленькую елочку, которой совершенно не холодно в офисе зимой, но совсем одиноко без огоньков, тем более что основной елке в офисе достались и игрушки, и гирлянды, а маленькой ничего. Но мы посчитали, что это не беда, а даже ее преимущество. Значит сделаем для нее не только уникальную гирлянду своими руками, но и сами выберем ей цвета светодиодов (возьмем цвета нашей компании: белый и голубой) и даже организуем ей беспроводное управление режимами по Zigbee-кнопке. А для гарантии безопасности еще и добавим автоматическое выключение по расписанию.

Модели устройств, файлы со сценариями автоматов, код для NodeMCU в конце статьи (не пытайтесь повторить это дома попробуйте повторить это дома!).

image

Собираем прототип


Создание прототипов это процесс сборки простой рабочей модели продукта или системы. Для начала построим его на макетной плате, а затем, как водится, красиво спаяем.

Итак, для маленькой гирлянды нам понадобится:

  • 12 белых и 6 голубых светодиодов, управление которыми производится независимо (назначение: гореть и радовать)
  • 2 резистора на 220 Ом, подбираемые исходя из расчета сопротивления и мощности по закону Ома (назначение: защита светодиодов от перегрева и выхода из строя)
  • 2 биполярных NPN транзистора (назначение: управляем транзистором маленьким током от управляющего пина, а пропускаем на диоды большой ток с выхода 3.3 В, так мы защищаем управляющий пин платы)
  • 2 резистора на 1 кОм на базу транзистора (назначение аналогичное, ограничиваем ток)
  • плата NodeMCU (назначение: подключение к IoT-платформе и управление транзисторами)
  • батарейки или блок питания (назначение: источник питания для платы)

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

Если изобразить на схеме, то это выглядит так:

image

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




Пишем код


Ниже представлен код для управления режимами гирлянды. Его функции:

  1. установить Wi-Fi соединение и подключиться к платформе;
  2. подписаться на команды сообщения с топиками led_on, led_off, led_attenuation, led_flashing и выполнять соответствующие действия по управлению светодиодами.

Команды led_on и led_off включают и выключают гирлянду, а команды led_attenuation и led_flashing задают режимы плавного горения и быстрого мигания с периодом, указанным в payload команды.

Обратите внимание, в коде мы используем библиотека Sheduler, которая нужна для того, чтобы одновременно запускать несколько потоков с задачами. Если этого не сделать, то при запуске бесконечного цикла горения светодиодов параллельно получать команды с платформы уже не получится.

#include "Arduino.h"#include "Scheduler.h"      /* https://github.com/nrwiersma/ESP8266Scheduler */#include "EspMQTTClient.h"  /* https://github.com/plapointe6/EspMQTTClient */                           /* https://github.com/knolleary/pubsubclient */// Даем разумные имена для пинов, управляемых светодиодами#define BLUE_LED_PIN 12#define WHITE_LED_PIN 13EspMQTTClient client( "<wifi-ssid>", "<wifi-password>" "dev.rightech.io", "<ric-mqtt-client-id>");// Задача для обработки поступающих командclass ClientTask : public Task { public:   void loop() {     client.loop();   }} client_task;// Задача для включения светодиодовclass LedOnTask : public Task { protected:   void loop()   {     digitalWrite(WHITE_LED_PIN, HIGH);     digitalWrite(BLUE_LED_PIN, HIGH);     shouldRunValue = false; // останавливаем этот цикл сразу после включения   }   bool shouldRun()   {     return shouldRunValue;   } public:   bool shouldRunValue = false;} led_on_task;// Задача для выключения светодиодовclass LedOffTask : public Task { protected:   void loop()   {     digitalWrite(WHITE_LED_PIN, LOW);     digitalWrite(BLUE_LED_PIN, LOW);     shouldRunValue = false; // останавливаем этот цикл сразу после выключения   }   bool shouldRun()   {     return shouldRunValue;   } public:   bool shouldRunValue = false;} led_off_task;// Задача для плавного горения светодиодов в противофазеclass LedAttenuationTask : public Task { protected:   void loop()   {     // Вычисляем задержку на один проход цикла в зависимости от полученного в payload значения     float delayValue = period.toInt() * 1000 /*в миллисекунды*/ / 2 /*на два цикла*/ / 1024 /*на каждую итерацию в цикле*/;     for (int i = 0; i <= 1023; i++) {       analogWrite(WHITE_LED_PIN, i); // горит ярче       analogWrite(BLUE_LED_PIN, 1023 - i); // тускнеет       delay(delayValue);     }     for (int i = 1023; i >= 0; i--) {       analogWrite(WHITE_LED_PIN, i); // тускнеет       analogWrite(BLUE_LED_PIN, 1023 - i); // горит ярче       delay(delayValue);     }   }   bool shouldRun()   {     updateDelayTimer();     if (isDelayed()) return false;     if (!run_group_active) return false;     return shouldRunValue;   } public:   bool shouldRunValue = false;   String period;} led_attenuation_task;// Задача для быстрого мигания светодиодов в противофазеclass LedFlashingTask : public Task { protected:   void loop()   {     float delayValue = period.toInt() * 1000 /*в миллисекунды*/;     digitalWrite(WHITE_LED_PIN, HIGH);     digitalWrite(BLUE_LED_PIN, LOW);     delay(delayValue);     digitalWrite(WHITE_LED_PIN, LOW);     digitalWrite(BLUE_LED_PIN, HIGH);     delay(delayValue);   }   bool shouldRun()   {     updateDelayTimer();     if (isDelayed()) return false;     if (!run_group_active) return false;     return shouldRunValue;   } public:   bool shouldRunValue = false;   String period;} led_flashing_task;void setup() { // Настраиваем пины в режим выхода, т.е. в режим источника напряжения pinMode(WHITE_LED_PIN, OUTPUT); pinMode(BLUE_LED_PIN, OUTPUT); // Библиотека Scheduler позволяет при необходимости запустить несколько потоков Scheduler.start(&led_on_task); Scheduler.start(&led_off_task); Scheduler.start(&led_attenuation_task); Scheduler.start(&led_flashing_task); Scheduler.start(&client_task); Scheduler.begin();}void onConnectionEstablished() { // Подписываемся на команды и запускаем нужный поток путем изменения переменной shouldRunValue client.subscribe("led_on", [] (const String & payload)  {   client.publish("base/state/light", "on");   led_off_task.shouldRunValue = false;   led_attenuation_task.shouldRunValue = false;   led_flashing_task.shouldRunValue = false;   led_on_task.shouldRunValue = true; }); client.subscribe("led_off", [] (const String & payload)  {   client.publish("base/state/light", "off");   led_on_task.shouldRunValue = false;   led_attenuation_task.shouldRunValue = false;   led_flashing_task.shouldRunValue = false;   led_off_task.shouldRunValue = true; }); client.subscribe("led_attenuation", [] (const String & payload)  {   client.publish("base/state/light", "attenuation " + payload + " sec");   led_on_task.shouldRunValue = false;   led_off_task.shouldRunValue = false;   led_flashing_task.shouldRunValue = false;   led_attenuation_task.period = payload;   led_attenuation_task.shouldRunValue = true; }); client.subscribe("led_flashing", [] (const String & payload)  {   client.publish("base/state/light", "flashing " + payload + " sec");   led_on_task.shouldRunValue = false;   led_off_task.shouldRunValue = false;   led_attenuation_task.shouldRunValue = false;   led_flashing_task.period = payload;   led_flashing_task.shouldRunValue = true; });}void loop() {}

Подключаем к платформе Rightech IoT Cloud


Подключение гирлянды:


1) Создаем модель




2) Создаем объект с этой моделью




Подключение кнопки:


1) Создаем модель




2) Создаем объект с этой моделью




Подробнее о том, как подключать ZigBee устройства, можно посмотреть в видеоуроке и почитать в статье.

Разрабатываем сценарий работы


От сценария автоматизации мы хотим следующей логики:

1) один клик (single) режим постоянного свечения и выключения;

2) два клика (double) режим плавного свечения;

3) три клика (triple) режим мигания;

4) после 20:00 автоматическое выключение гирлянды (здесь также можно использовать не просто расписание, а данные еще из одного объекта СКУДа, который собирает информацию о том, есть ли люди в офисе. Если вам интересен материал по такой теме, дайте обратную связь в комментариях ).

Готовый автомат




Давайте вкратце разберем, что тут происходит и зачем:

  1. Первым делом при старте автомата запускаем планировщик, который выключит гирлянду по расписанию, обезопасив нас от забывчивости. Запустили и забыли, он будет срабатывать каждый день автоматически.
  2. В следующем состоянии не делаем ничего, просто ждем нажатия кнопки. В это состояние мы возвращаемся каждый раз после отработки определенного режима гирлянды. Из него есть переход по событию получения данных и срабатыванию планировщика.
  3. Если получили какой-то пакет от кнопки, то переходим в состояние Получен пакет, из которого по таймеру и типу клика переходим в соответствующие режимы. Вы можете спросить, зачем тут таймер. А причина в том, что кнопка работает довольно интересненько. При нажатии три раза, она сначала присылает пакет с double, а сразу за ним triple. Такой нюанс мы и обходим таймером, иначе срабатывало бы по неактуальному клику.
  4. Также есть промежуточное состояние для одинарного клика. Как мы помним, вкл/выкл у нас работают по одному и тому же событию. Поэтому, если гирлянда не выключена (находится в любом из режимов активной работы), то мы ее выключаем, а если выключена, то включаем.

Запускаем автомат на наших объектах, проверяем фуууух, работает! Время паять!




Собираем готовое устройство


Самый простой вариант пайки гирлянды это один за другим спаивать светодиоды, предварительно надевая термоусадку. Примерно вот так:

image

Но можно пойти немного другим путем сделать не просто гирлянду, которой мы обвяжем елку, облачив ее дополнительно во все эти провода. Вместо этого на каждую веточку посадим по светодиоду (в цветочках это смотрится особенно чудесно, см. итоговое фото), стянем провода по стеблю вниз и спаяем, спрятав всю электронику в горшочке. На выходе остается только разъем под кабель питания. Ювелирно, аккуратно и очень симпатично получается. Судите сами.

image

термоусадку нагреваем паяльным феном

image

помещаем провод перед пайкой в канифоль (в таком случае не образуется тонкой оксидной пленки на поверхности провода, в результате спайка проходит легче и получается надежнее)

image

и лудим (наносим небольшой слой припоя)

image

проводок готов воссоединяться со светодиодом

image

соединяем (паяем поверхности, на которых уже есть припой)

image

фиксируем на веточке, сгибая ножки (необходимо предварительно оставить не менее 10 мм) светодиода

image

на данном этапе проводим последнее тестирование

image

готово!




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

С наступающим праздником!

Материалы к статье


image
Подробнее..

Умный дозатор таблеток или мой первый опыт в IoT

22.01.2021 16:14:24 | Автор: admin

Автоматический дозатор


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


Немного про IT Академию Samsung


Перед тем, как рассказать про мою разработку, хочу поделиться впечатлениями от первых занятий в IT Академии Samsung по треку Интернет вещей, который я прошел в НГТУ в прошлом учебном году. Началось всё с прошивки контроллера STM32 RIOT OSИ всё это через Linux и командную строку. Честно скажу, что опыт незабываемый настолько, что я уже начал переживать, что в 2020 году люди все еще программируют в командной строке и после компиляции заливают образ вручную на контроллер. Но уже на следующем занятии нас познакомили с инструментами, которыми пользуются разработчики, а всё предыдущее было для демонстрации того, что происходит, когда мы нажимаем волшебную кнопку Build в среде разработки. Хочу также отметить, что за весь курс мы ни разу не программировали с помощью фреймворка Arduino, что, как по мне, является огромным плюсом, поскольку в реальных задачах и на производствах данный фреймворк (я надеюсь) не используется. Нас познакомили с Mbed, RTOS, а также ESP-IDF (которая, к слову, базируется на FreeRTOS). Мне нравилось, что каждый кейс начинался с объяснения, для чего будет использоваться данное устройство, и какие технологии уместно применять в нем.


По окончании обучения каждый студент представлял свой проект по Интернету вещей для получения сертификата IT Академии Samsung. Это мог быть простой светильник с функцией включения по Bluetooth, или что-то посложнее Мне хотелось сделать устройство, которое будет сложным с точки зрения программирования, при этом решать действительно важную проблему. Поэтому я остановился на умном дозаторе таблеток.


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


Про разработку


Как же я пришёл к тому устройству, что есть сейчас, получившему название AutoPill?


Шаг 1. Определение функционала и выбор микроконтроллера


Поскольку с идеей я разобрался, необходимо было переходить непосредственно к реализации. Я опросил знакомых, что им бы хотелось видеть в этом устройстве. Отсёк те идеи, которые посчитал не моим путём, и составил описание функционала будущего устройства получилось около 15 пунктов. А затем снова опросил тех же знакомых со словами выбери из данного списка самые важные, по твоему мнению, пункты. Это позволило уже на начальном этапе определить тот основной функционал, который нужен именно потребителю, а не тот, который проще всего реализовать или интересен мне.


Итак, что я хотел получить на выходе? Как мне казалось на тот момент, успеть это выполнить к сроку (конец учебного года) вполне реально.


  • Устройство должно быть таким, чтобы пользователь (пациент) не мог по ошибке открыть сектора с хранящимися препаратами. Сектора должны открываться по расписанию автоматически и блокироваться при открытии следующего отсека.
  • Устройство должно сигнализировать пользователю о необходимости принять новую порцию препаратов.
  • Отсеков должно хватать более чем на один день.
  • Конструкция устройства должна быть компактной (в качестве примера большинство приводили шкатулки или небольшую коробку).
  • Гибкая настройка расписания: возможность задать периодичность с шагом в 30 минут.
  • Возможность посмотреть, принял пользователь препараты или нет.

И необходимо проработать следующие особенности:


  • Как открывать/закрывать отсеки?
  • Как понять, когда пользователь принял препараты, чтобы отключить индикацию?
  • Как сообщать пользователю состояние?
  • Как настраивать устройство?

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


Чтобы понять всё остальное, необходимо было разработать конструкцию таблетницы. На этом этапе я также выбрал микроконтроллер ESP32, поскольку у него есть множество встроенных возможностей, которые позволят в дальнейшем значительно расширить платформу (например, ESP-NOW, ESP-Touch и ESP-Mesh), а бонусом была поддержка двух необходимых протоколов связи WiFi и Bluetooth.


Шаг 2. Конструкция устройства


Перед тем, как начать разрабатывать конструкцию устройства, я рассмотрел множество вариантов конструкций обычных таблетниц как оказалось, их не так уж много.


Возможные типы дозаторов
  1. Набор контейнеров самый популярный тип, модификаций которых несколько десятков, вот один из них
    Набор контейнеров

    Aidapt Deluxe VM930AB
  2. Карманная таблетка этот тип я назвал так, потому что он округлой формы, с отсеками, расположенными по кругу. В центре есть место для таймера, который может сигнализировать о необходимости принятия лекарств
    Карманная "таблетка"

    Bradex недельная с таймером KZ 0439

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


Какие дозаторы были найдены


Я принял решение разработать свой корпус устройства, не забывая и о функциональности, обозначенной в шаге 1.


Для того, чтобы разработать конструкцию, было бы неплохо выучить какой-нибудь САПР. К счастью, в лицее я научился работать в Компас-3D, что сильно упростило задачу. Вторая проблема изучить, из каких материалов можно сделать из 3D модели настоящий прототип. Мой выбор пал на 3D-принтеры, поскольку это, по моему мнению, самая простая возможность создать прототип и напечатать деталь практически любой сложности.


Итак, представляю самую первую версию сборки из, на тот момент, трёх деталей


Инженерам не открывать!

1я версия устройства


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


  1. Не поленитесь посмотреть размеры столов самых популярных принтеров, чтобы у вас был широкий выбор, где заказать печать или попросить по дружбе
  2. При проектировании, если вы раньше ни разу не видели принтеры вживую (как я, например), посмотрите, как эта технология реализована, и какие детали ей сложнее всего печатать, постарайтесь оптимизировать модель под более простую печать для уменьшения времени печати и количества брака. Наглядный пример, как делать не надо, можете посмотреть на первую версию крышки устройства. У неё очень пологий угол наклона, что делает печать без поддержек невозможной, и даже с поддержками шанс брака очень велик, так как пластик при такой толщине может просто не сцепиться.
  3. Не печатайте на плохо откалиброванных принтерах или принтерах с низкой точностью печати, особенно это касается конструктивно важных деталей (шестерни). Тоже немного негативного опыта я получил при печати основы на дешёвом принтере: вышло нарушение соосности деталей, что создало множество проблем, начиная с неравномерного трения при разных положениях отсеков, и заканчивая длительной подгонкой деталей.

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


Сборка последней версии


На данной иллюстративной сборке не видно таких элементов, как:


  • нижняя крышка основы, в которой расположен редуктор и посадочные места для всех электронных компонентов;
  • шестерня (к сожалению, пришлось просчитывать свою шестерню для плоскоцилиндрической передачи), в остальном редукторе используются шестерни из первого попавшегося набора шестерёнок для электроконструктора.

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


Шаг 3. Электроника


Конечно же, разработка корпуса не происходит изолированно, при разработке должны учитываться размеры всей электронной начинки, которую вы собираетесь расположить внутри. А на момент создания прототипа, когда вы используете заранее распаянные датчики на платах, места потребуется немного больше, и необходимо также учитывать расположение и размеры плат. Что же требуется, чтобы таблетница заработала?


  1. Микроконтроллер. В моём случае я взял ESP32 Dev Kit с уже распаянным на плате понижающим регулятором напряжения, а также отладчиком.
    ESP32 Dev Kit
    ESP32 Dev Kit
  2. DC мотор мотор коллекторного типа, наверное, один из самых популярных, используется в радиоигрушках.
    DC двигатель
    DC двигатель
    Рабочее напряжение: 3 Вольт ~ 8 Вольт
    Ток потребления при напряжении 3,6В: 240 мА
    Тип двигателя: коллекторный
    Вес: 26 гр
  3. Щелевой датчик датчик, необходимый для отслеживания количество оборотов редуктора. В устройстве стоит датчик с уже распаянным компаратором LM393 (на изображении приведён датчик непосредственно с платой развязки).
    Щелевой датчик ITR9608
    Щелевой датчик
    Рабочее напряжение: 3.3 Вольт ~5.0 Вольт
    Ток потребления энкодера: 1.4 мА
    Ширина паза в щелевом датчике: 5 мм
    Вес: 8 гр
    Рабочая температура: от 0 до +70
  4. Датчик наклона датчик необходим, чтобы определять, взял ли пациент лекарство из устройства. Поскольку отсеки глубокие и достать пальцем сложно, предполагается что пользователь будет вынимать необходимые препараты, наклоняя таблетницу.
    Датчик наклона SW-200D
    Датчик наклона SW-200D
    Рабочее напряжение: до 12 В
    Потребляемый ток: до 20 мА
    Время отклика: 2 мс
    Время жизни: 100000 циклов
    Размер: 12 x 3,6 мм
    Вес: менее 1 гр
    Рабочая температура: от -40 до +80

Помимо датчиков, также использовался MOSFET-транзистор, который служил ключом для запуска и остановки мотора. Собственно, это была вся электроника.


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


Шаг 4. ПО


Хочется отметить, что, конечно, к шагам 2-4 после первой итерации я возвращался не раз, т.к. шла и доработка конструкции, и создание ПО. И хочется уточнить, что шаги ни в коем случае не выполнялись одновременно, а именно доводились до логического завершения, потому что ПО сильно зависело от текущей конструкции.


Самый первый вопрос разработчика ПО для IoT будет следующим (по крайней мере для меня): существует ли IDE для разработки устройств IoT? Почти для каждого микроконтроллера существует своя IDE, но лично я пользовался универсальной средой PlatofrmIO. В течение всего цикла разработки я ни разу не пожалел об этом решении.


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


Язык, на котором написан код проекта: C. Честно сказать, после нескольких лет написания кода на языках Java, Kotlin и иногда C#, я, хоть и был морально готов к этому испытанию, но не ожидал, что встречу столько неудобств. Но в итоге это оказался очень классный опыт.


Прежде чем приступить к разработке ПО, я изучил на просторах GitHub, как вообще пишут программы под ESP-IDF, и, к моему большому удивлению, результатов (если не считать библиотеки с примерами) оказалось крайне мало. Ладно, подумал я, и решил разработать свою архитектуру для ПО.


Вся программа была разбита на модули. Каждый модуль отвечал за точно описанную функциональность, при этом, если одному модулю необходимы другие модули для работы (например, модулю сервера необходим модуль аутентификации), то он должен сам их инициализировать. Тем самым обеспечивается самостоятельность каждого модуля. При этом, если модулю необходимо обрабатывать какие-то пользовательские события, то это должно происходить исключительно в главном классе, а сам модуль ничего не должен знать об этом. Данное условие позволяет использовать уже написанные модули в других проектах без необходимости переписывания их логики.


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


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


  1. Работа с периферией. Самый очевидный модуль, причём я принял решение разработать отдельные модули для отображения и для входных данных. Как впоследствии оказалось, достаточно было сделать только тот, что для входа.
  2. Подключение устройства к Wi-Fi. Я решил именно подключаться к Wi-Fi и разворачивать свой мини-сервер, поскольку станций Интернета вещей не было ни у кого из опрошенных, а Wi-Fi есть дома всегда. Подключение производилось через WPS, с возможностью изменения в настройках.
  3. Создание HTTP-сервера на устройстве. Очевидно, что для такого сегмента использование протокола HTTP неудачное решение, но на данный момент я его не заменил, поскольку мне важна возможность использования устройства в изолированной сети, что не даёт возможности автоматически продлевать сертификат, а с самоподписанными сертификатами на сервер пропускает разве что Internet Explorer, и то с предупреждениями о том, что это всё мошенничество.
  4. Реализация модуля безопасной авторизации. В данном случае мы говорим о Digest-аутентификации. Данная аутентификация позволяет в пределах локальной сети сделать устройство максимально устойчивым к взлому.
  5. Модуль планировщика. Наверное, самый важный модуль, который должен поворачивать сектор точно при наступлении необходимого времени. При этом, данный модуль должен также поддерживать синхронизацию времени (т.е. перераспределение задач и автоматическое устранение ошибок)

Это те модули, которые были первостепенны, и без которых устройство просто не могло существовать.


Но, приступая к реализации самого, казалось бы, банального, первого модуля для работы с периферией, я столкнулся с объемной и непонятной документацией. Я думаю, это один из основных факторов, почему каких-либо готовых проектов на ESP-IDF мало. К счастью, у разработчиков есть GitHub, который, благодаря примерам, сильно упрощает понимание. Единственное, не забудьте выбрать нужную ветку с вашей версией ESP-IDF! Пожалуй, это единственная проблема данного фреймворка. А в остальном он очень неплох. Внутри него есть практически всё, что раньше вы добавляли с помощью библиотек: WiFi, WPS, HTTP-сервер, NTP, различные функции хэширования и многое другое.


Веб-интерфейс
Таблетница AutoPill общается с внешним миром при помощи API, к которому может обратиться как веб-интерфейс, так и любая внешняя система (актуально это будет, если вы хотите настраивать несколько таблетниц из одного места). Поэтому устройство может использоваться и в домашних условиях, и в учреждениях, где таких таблетниц может быть множество.


Варианты использования устройства


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


Веб-консоль настройки

Веб-консоль


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


Что получилось?


Сам код устройства находится в открытом доступе, и вы можете найти его здесь.


Давайте подытожим.


Для кого разработан AutoPill? Целевая аудитория люди с деменцией и плохой памятью, которые принимают медицинские препараты на постоянной основе. Стоит учитывать, что данное устройство не способно полностью заменить близкого человека или медицинского работника, который выдаёт медицинские препараты, но способно значительно упростить процесс выдачи и контроля принятия лекарств пациентом. Необходимо лишь раз в неделю или реже раскладывать препараты по секторам, а далее удалённо отслеживать принятие препаратов.


Как подключить AutoPill? При первом запуске устройства или смены точки доступа это можно сделать с помощью WPS или протокола ESP-Touch (через приложение на смартфоне).


На данный момент устройство работает от сети, но в дальнейшем будет добавлена возможность работы от аккумулятора, при этом внимание будет уделено режиму энергосбережения (в т.ч. автономной работе, либо работе в режиме клиента, когда в качестве сервера будет выступать станция IoT).


За счёт червячной передачи в редукторе пользователь не может провернуть секцию вручную. Конечно, сорвать пластиковую шестерню можно, но это потребует значительных усилий. Кроме того, в конструкции есть простейший замок, который открывается и закрывается обычной прямой отвёрткой. Согласитесь, эти варианты исключают случайный доступ к внеочередной порции препаратов.


Видео о проекте:



Что дальше?


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


Сейчас, помимо полировки уже существующих функций устройства, передо мной стоит очень важная задача уменьшение энергопотребления. Кроме того, я работаю над интеграцией устройства в систему SmartThings. Это позволит продублировать все автономные функции на хабе или в облаке, при этом само устройство сможет более эффективно расходовать энергию. Помимо этого, после интеграции AutoPill сможет не просто подавать сигнал с помощью собственных встроенных возможностей, но использовать и носимые устройства и умные колонки для оповещения пользователя о тех или иных событиях.


Владимир Шперлинг

Владимир Шперлинг
vladimir-shperling@yandex.ru
Kotlin, Java, C#-разработчик
Победитель финала конкурса проектов IT Школы Samsung, 2016
Победитель конкурса Школа VR 360, 2018
Победитель конкурса IT Академии в треке Интернет вещей, 2020

Подробнее..

Системы контроля управления доступом в IoT умеем, знаем, практикуем

27.01.2021 14:17:26 | Автор: admin

И снова привет, мир!

В прошлой статье про IoT-елочку в голосовании многие отметили, что интересна тема управления устройствами в зависимости от количества человек в помещении. Это довольно масштабная задача, и мы предлагаем разделить ее решение на несколько этапов. Сегодня поговорим о системе контроля управления доступом (СКУД), которая, будучи подключенной к платформе интернета вещей Rightech IoT Cloud (далее по тексту - платформа), является базовым элементом в системе подсчета количества человек в офисе. Мы уже поверхностно освещали этот кейс в одной из статей, но сегодня рассмотрим этот проект более подробно и погрузимся в особенности исполнения.

СКУД?

Система контроля и управления доступом, СКУД (англ. Physical Access Control System, PACS) совокупность программно-аппаратных средств контроля и управления, главная цель которой - ограничение и регистрация входа-выхода объектов (людей, транспорта) на заданной территории через точки прохода: двери, ворота, КПП.

С чего все началось

Задача обеспечить контроль за входом-выходом в офисе возникла еще в те времена, когда у нас был выход на крышу с отличным видом на Москву, и поэтому часто приходили люди, не являющиеся нашими сотрудниками. Тогда мы решили принять какие-то меры по безопасности и установить СКУД.

Архитектура

Система открытия дверей по карте

В качестве модуля, отвечающего за обработку информации по считыванию бесконтактных карт, выбрали GATE-8000.

Основные достоинства контроллера:

  • формирование и хранение необходимой информации о факте открытия двери по карте и времени прохода человека в офис;

  • возможность автономной работы и защиты от зависания;

  • хранение 16 тысяч ключей и 8 тысяч событий;

  • простое подключение и управление;

  • российский производитель, хорошая документация с описанием работы контроллера.

Внешний вид платы с контроллеромВнешний вид платы с контроллером

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

Система взаимодействия с платформой

После того, как контроллер установили в систему по общей схеме подключения, а карты записали в память, мы уже обезопасили себя от прохода в офис посторонних. А дальше возник вопрос, как подключить этот контроллер к платформе Rightech ioT Cloud. Ведь очень здорово иметь а) графический интерфейс, в котором можно полистать историю всех проходов, б) возможность отправки команд на открытие двери удаленно, не отходя от рабочего места, например, для гостей или доставщика еды.

У контроллера нет выхода в Интернет и видимой возможности подключения к платформе, к тому же все события нужно принудительно считывать из его циклического буфера. Однако у него есть свой протокол обмена данными с компьютером управления, благодаря которому можно отправлять на контроллер команды, такие как считать из контроллера, записать в контроллер, открыть/закрыть замок и другие. Значит, нужно сделать некоторую программно-аппаратную прослойку между контроллером и платформой - агента, который будет отправлять команды на чтение событий и управление контроллером.

Обращаем внимание, что в данной архитектуре функция открытия двери при прикладывании карты не перестанет выполняться при отсутствии Интернета. За открытие двери и сбор информации отвечает контроллер СКУД, поэтому в случае потери Интернета, единственное, что нам грозит, - это то, что агент, который доставляет данные на платформу, не будет функционировать, так как не сможет получать команды на чтение буфера. Однако при восстановлении соединения все события считаются в полном объеме и не потеряются, так как они будут сохранены в буфере контроллера СКУД.

Аппаратная часть

Для начала нужно было выбрать устройство, которое будет всегда в активном состоянии с включенной программой-агентом в непосредственной близости от платы СКУД. Из многообразия микрокомпьютеров первое что попало под руку выбор пал на Raspberry Pi.

Дальше возник вопрос, как подсоединить GATE-8000 к Raspberry - то есть как подключить последовательный интерфейс RS485 от GATE к USB от микрокомпьютера. Начались поиски переходника USB-RS485. Первый вариант, который мы испробовали, - Espada за 200 рублей. Надежда на то, что маленький хлипкий китайский переходник заработает, была небольшой. Он и не заработал. Вместо нужных данных приходило что-то похожее по виду и размеру, но всё же не то. В чем было дело: в отсутствии гальванической развязки, невозможности поддерживать скорость 19200 bps или же просто в некачественной элементной базе, - загадка. Но после обращения к производителю GATE-8000, мы получили рекомендацию на более дорогой (в 10 раз) и громоздкий (но аккуратный и корпусированный) переходник Z-397, который заработал тут же как надо.

Программная часть

Начинаем разработку программы с определения, какие функции она должна выполнять.

  1. Что нужно - взаимодействие с GATE-8000 для отправки команд и получения данных.

    Как решим - изучим протокол GATE, напишем сериализатор и десериализатор данных, подключим библиотеку для работы с последовательным портом.

  2. Что нужно - взаимодействие с платформой для получения команд и отправки данных.

    Как решим - выберем для общения протокол MQTT, в коде воспользуемся готовой библиотекой Paho MQTT.

Итак, мы приступили к изучению протокола GATE-8000, который является закрытым, поэтому ниже рассказано только о некоторых его особенностях. Он достаточно низкоуровневый, и необходимо обращаться напрямую к регистрам памяти устройства. В документе по этому протоколу описаны кадры запросов от компьютера контроллеру и кадры ответов контроллера компьютеру. Меняя поля в кадре запроса, можно отправлять на устройство различные команды и получать информацию из регистров.

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

1) задавать всю логику работы в агенте;

2) использовать внешние запросы (от платформы).

Мы выбрали второй вариант и вынесли логику с конечного устройства на платформу (подробнее про сервис сценариев автоматизации >>>). Так ее легко адаптировать и подстроить, при этом код программы остается компактным и позволяет просто формировать команды для устройства, а платформа в свою очередь координирует отправку команд и их периодичность.

Всегда ли нужно выносить логику работы с устройства?

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

После того как мы внимательно изучили этот протокол, формат кадров и список команд, возникла первая сложность. Команды для чтения буфера, в котором содержатся события о том, кто и во сколько пришел, не оказалось. А ведь получить эту информацию - первоочередная задача. Понадобилось изучить карту памяти контроллера, чтобы определить адреса, по которым нужно считывать данные.

Карта памяти контроллера? WTF?

Под картой памяти контроллера (термин из протокола) имеется в виду таблица с описанием заполнения регистров памяти, а не микрофлешка =).

Следующая особенность работы с контроллером в том, что за один цикл чтения можно получить только 12 событий, по 8 байт на каждое. А на каждый проход человека в офис генерируется уже два события:

1) найден ключ в банке ключей (банк ключей - еще один блок в распределенной памяти контроллера);

2) состоялся проход (если он, конечно, состоялся).

Ниже представлен фрагмент кода на С++, реализующий метод одного цикла чтения буфера.

bool SerialPortInlet::readBufferCycle(unsigned short& bottom, unsigned short const& top, unsigned char& u_lowerBound,    unsigned char& l_lowerBound, std::vector<unsigned char>& readBuffer, std::string& result){// Подсчет байтов, которые необходимо считатьunsigned short byteCountTmp = top - bottom;BOOST_LOG_SEV(log_, logging::info) << "Need read " << byteCountTmp << " byte";unsigned char byteCount;// За один цикл нельзя прочитать более 12 событий (96 байт)byteCount = byteCountTmp > 0x60 ? 0x60 : (unsigned char)byteCountTmp;BOOST_LOG_SEV(log_, logging::info) << "Read " << +byteCount << " byte";// Описываем тело командыstd::vector<unsigned char> body = {0x02, 0xA0, byteCount, u_lowerBound, l_lowerBound};std::vector<unsigned char> command;// Получаем полный текст командыgenerateComplexCommand(command, Command::BYTE_CODE_READ, body);// Если не удалось по каким-то причинам отправить команду (например, конечное устройство не подключено), возвращается falseif (!sendCommand(command, result)){    return false;}// Иначе отправляем ответ с устройства на парсинг по событиямSerialPortType::Answer answerEvents;if(!Parsers::parserAnswer(log_, result, answerEvents, Command::BYTE_CODE_READ)){    BOOST_LOG_SEV(log_, logging::error) << "Failed parse buffer reading";    return false;}readBuffer.insert(readBuffer.end(), answerEvents.body.begin(), answerEvents.body.end());// Сдвигаем нижнюю границу буфера для чтения следующих событийbottom = bottom + byteCount;u_lowerBound = (unsigned char)(bottom >> 8) ;l_lowerBound = (unsigned char)bottom;return true;}

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

Байтстаффинг?

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

Пример байтстаффинга из документацииПример байтстаффинга из документации

Полная структурная схема разработанной системы выглядит так.

Работоспособность всех устройств было очень удобно проверять с помощью графического последовательного терминала СuteCom. После успешного тестирования программа была поставлена на автозапуск, а Raspberry отправилась жить на потолке рядом с платой СКУДа.

Один делает, другой смотрит, третий фотографирует, огнетушитель придерживает дверь - настоящая командная работа =)Один делает, другой смотрит, третий фотографирует, огнетушитель придерживает дверь - настоящая командная работа =)

Работа на платформе Rightech IoT Cloud

Модель

Основные данные с контроллера - это события, на платформу они приходит в формате JSON и включают в себя поля

  • eventTime - время наступления события;

  • eventCode - код события;

  • keyNumber - номер карты сотрудника (поле может быть пустым, если событие вызвано не картой).

Модель устройства выглядит следующим образом.

Посмотреть оригинал >>>

Возможные события:

  • нажата кнопка звонка;

  • неопознанный ключ на входе;

  • неопознанный ключ на выходе;

  • ключ найден в банке ключей при входе;

  • ключ найден в банке ключей при выходе;

  • открывание оператором по сети;

  • дверь заблокирована оператором;

  • дверь оставлена открытой после входа;

  • дверь оставлена открытой после выхода;

  • проход состоялся на вход;

  • проход состоялся на выход;

  • перезагрузка контроллера.

Объект

Интерфейс объекта полностью формируется согласно разработанной модели.

Интерфейс истории журнала объектаИнтерфейс истории журнала объекта

Посмотреть оригинал >>>

Интерфейс командИнтерфейс команд

Ура, теперь, собравшись на кухне офиса в ожидании пиццы на праздник, можно никуда не идти, а просто открыть мобильное приложение и нажать кнопку открытия двери для курьера!

Автомат

Можно заметить, что есть команда не только на чтение буфера событий, но и на запись новых границ. В памяти контроллера хранятся границы буфера - начало и конец. Когда на устройство приходит команда чтения, из памяти берутся эти границы и в их пределах происходит чтение из буфера событий. Граница конца буфера сдвигается автоматически на контроллере при получении новых событий. А вот начальную границу буфера нужно перезаписать (указав конечную границу после прошедшего чтения), чтобы не прочитать одни и те же данные повторно. Но это необходимо сделать только после того, как данные о событиях успешно отправлены на платформу.

Зафиксировать успешное получение данных и затем отправить команду на перезапись начальной границы удобно в автомате.


Посмотреть оригинал >>>

Здесь виден цикл <чтение>-<запись новой границы буфера>-<ожидание таймера> (сейчас события считываются каждые 30 секунд).

  1. В состоянии Read events читаем новые события.

  2. В состоянии Clear buffer записываем новую границу.

  3. В состоянии Await timer ожидаем начала нового цикла.

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

Дальнейшее использование собранных данных

Данный проект нашел свое продолжение в интеграции с нашей внутренней CRM системой, в которой на вкладке информации о сотрудниках всегда видны актуальные сведения о том, кто находится или отсутствует в офисе.

Также отображается время входа/выхода из офиса, считается суммарное количество часов в месяц.

Посмотреть оригинал >>>

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

Забор данных из платформы производится по REST API. API платформы предоставляет возможность работы, взаимодействия и использования сущностей платформы и их данных в таких внешних системах, как веб-порталы, мобильные и веб-приложения или, как в нашем случае, - CRM системах.

Посмотреть проект, в котором есть пример настройки взаимодействия и получения данных с платформы >>>


Теперь мы знаем немного больше о том, как может работать СКУД в IoT-проектах. В следующих материалах рассмотрим, как рассчитать на базе полученной информации количество человек в офисе и какие практические применения есть у этой идеи.

Подробнее..

Категории

Последние комментарии

  • Имя: Макс
    24.08.2022 | 11:28
    Я разраб в IT компании, работаю на арбитражную команду. Мы работаем с приламы и сайтами, при работе замечаются постоянные баны и лаги. Пацаны посоветовали сервис по анализу исходного кода,https://app Подробнее..
  • Имя: 9055410337
    20.08.2022 | 17:41
    поможем пишите в телеграм Подробнее..
  • Имя: sabbat
    17.08.2022 | 20:42
    Охренеть.. это просто шикарная статья, феноменально круто. Большое спасибо за разбор! Надеюсь как-нибудь с тобой связаться для обсуждений чего-либо) Подробнее..
  • Имя: Мария
    09.08.2022 | 14:44
    Добрый день. Если обладаете такой информацией, то подскажите, пожалуйста, где можно найти много-много материала по Yggdrasil и его уязвимостях для написания диплома? Благодарю. Подробнее..
© 2006-2024, personeltest.ru