Анализ двоичного содержимого нефиксированного формата с пользовательским преобразованием JavaScript в Vorto - PullRequest
1 голос
/ 16 октября 2019

В настоящее время мы используем Vorto в основном в качестве нормализованного формата и начинаем изучать использование механизма отображения для сопоставления различных форматов полезной нагрузки с моделью Vorto. Я более или менее понимаю, как сопоставить свойства функциональных блоков из JSON или двоичной полезной нагрузки, используя xpath и функции преобразования. Однако я не понимаю, как поддерживать синтаксический анализ двоичного содержимого нефиксированного формата с помощью этого метода. Например, у нас есть готовый датчик LoRaWAN, который передает в следующем формате: <length><frame type>[<sensor-id><sensor-value>] где длина - это общая длина кадра, а идентификатор датчика (например, температура, влажность, батарея, ...) описывает, как анализировать датчик-значение (то есть длина, тип данных). В одном кадре несколько из этих показаний могут присутствовать в случайном порядке.

С анализом это можно легко сделать, например, в loraserver.io, используя небольшую функцию javascript, которая перебирает все байты, и возвращает проанализированные свойства. Точно так же будет работать в движке картографирования полезной нагрузки Ditto afaik. Тем не менее, в настоящее время я не вижу, как сделать что-то подобное в картировании Vorto. Конечно, это только один конкретный пример датчика, но на рынке существует больше примеров, использующих подобный динамический формат полезной нагрузки. Я знаю, что уже существует открытая проблема (# 1535) для улучшения документации, но было бы полезно узнать, возможен ли такой гибкий синтаксический анализ с использованием сопоставления DSL.

Я попытался передать необработанные полезные данные в виде байтового массива в функцию javascript. Чтобы проверить это, я продублировал org.eclipse.vorto.mapping.engine.converter.binary.BinaryMappingTest#testMappingBinaryContaining2DataPoints и адаптировал модель для использования пользовательской функции javascript, такой как

    evaluator.addScriptFunction(new ScriptClassFunction("extractTemperature",
"function extractTemperature(value) { " +
        " print(\"parameter of type \" + typeof value + \", value = \" + value);" +
        " print(value[1]);" +
        "}"));

. Вывод этой функции:

parameter of type number, value = 1
undefined

Где значение1 является первым элементом используемого байтового массива.

Таким образом, функция, кажется, не получает параметр как байтарный массив. Модель настроена на .withXPathStereotype("custom:extractTemperature(data)", "demo"), поэтому полезная нагрузка передается (как BinaryData) так же, как в тесте testMappingBinaryContaining2DataPoints (.withXPathStereotype("custom:convert(vorto_conversion1:byteArrayToInt(data,0,0,0,2))", "demo")). Единственное отличие, которое я вижу сейчас, состоит в том, что в тесте testMappingBinaryContaining2DataPoints заключается в том, что параметр byetarray передается функции Java вместо функции javascript. Или я что-то упустил?

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

На gitter я получил следующий ответ (вместе с предложением перенести обсуждение на SO)

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

Однако я не думаю, что это решение проблемы. Как упомянуто выше, это только один пример стандартного формата полезной нагрузки датчика, и я не вижу, как это можно обобщить настолько, чтобы включить его в качестве универсальной функции в механизм отображения. И я не думаю, что нужно реализовывать преобразование для конкретного датчика в Java, поскольку (как конечный пользователь платформы IoT, желающий развернуть новый тип датчика), его сложнее разрабатывать и развертывать, чем небольшой JavaScript-кодфункция, которая может быть изменена во время выполнения в спецификации отображения. Я вижу большую ценность в возможности делать простые отображения в javascript, точно так же, как это можно сделать, например, в loraserver.io и Eclipse Ditto .

Я думаю, что возможность передать байтовый массив в javascript - это первый шаг. Также мне интересно, где именно риск в разрешении циклов в JavaScript? Например, Ditto также имеет некоторые ограничения в изолированной программной среде javascript ( см. Здесь ), но это допускает циклы и только предотвращает бесконечные циклы и рекурсию. Они заявляют следующее:

Использование Rhino вместо Nashorn, более нового движка JavaScript, поставляемого с Java, дает преимущество, заключающееся в том, что песочница может применяться лучше. Требуется песочница для разных сценариев полезной нагрузки, поскольку Ditto предназначен для работы в качестве облачной службы, где для нескольких арендаторов одновременно управляются несколько соединений с разными конечными точками. Это требует изоляции каждого отдельного сценария, чтобы избежать вмешательства в другие сценарии и защитить JVM, выполняющую сценарий, от выполнения вредоносного кода.

Если бы использование Rhino в Vorto также позволяло контролировать риски, которые вы видитеи разрешить создание цикла в отображении Vorto?

PS: может кто-то с достаточным количеством очков репутации SO добавит тег eclipse-vorto, пожалуйста?

1 Ответ

1 голос
/ 17 октября 2019

Я создал проблему для вашего запроса на поддержку этого в конвертерах Javascript: https://github.com/eclipse/vorto/issues/2029

Как указано в проблеме, в качестве текущего обходного пути вы можете зарегистрировать свою собственную функцию конвертера с помощьюJava и повторно используйте эту функцию в ваших отображениях. В этих функциях Java-конвертера у вас есть все возможности для преобразования языка Java для извлечения нужного свойства из произвольного списка. Чтобы узнать, как реализовать собственную функцию преобразования с помощью Java, посмотрите здесь: https://github.com/eclipse/vorto/tree/master/mapping-engine#Advanced-Usage

...