Реализация драйвера

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

Глобальная настройка и настройка отдельной учетной записи

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

Чтобы добавить общие и пользовательские настройки, используйте метод globalInit() и userInit(). Их реализация должна вызывать createGlobalConfigContext() и createUserConfigContext(), а также предоставлять глобальные и пользовательские настройки VariableDefinition. Эти настройки будут видны системным администраторам, а их значения сохранятся в БД. Переменные должны принадлежать к группе "по умолчанию", доступной как константа ContextUtils.GROUP_DEFAULT.

Чтобы получить доступ к значениям настроек из любого метода плагина, выберите контексты общей и пользовательской настройки, используя getGlobalConfigContext() или getUserConfigContext(), а затем вызовите Context.getVariable() , чтобы забрать экземпляры DataTable, представляющие значения установок.

Установка контекста устройства

SberMobile Server вызывает метод драйвера setupDeviceContext(), когда создана новая учетная запись устройства, или же когда запускается сервер. Метод получает экземпляр интерфейса DeviceContext , которым является Контекст Устройства, отражающий учетную запись этого устройства. Вызовите super.setupDeviceContext() , чтобы сохранить его ссылку внутри AbstractDeviceDriver.  Она будет доступна через метод getDeviceContext().

Основная цель setupDeviceContext() заключается в добавлении специфичных для устройства параметров связи. Они добавляются в виде переменных контекста, принадлежащих группе переменных ContextUtils.GROUP_ACCESS. Система подсказывает оператору отредактировать эти настройки в момент создания учетной записи устройства, и в последующем доступ к ним осуществляется через действие Редактировать Свойства Устройства.

Параметрыв связи следует добавить к контексту устройства, используя метод Context.addVariableDefinition().

Актуальные значения, заданные пользователем, можно затем забрать из DeviceContext , используя Context.getVariable(), например из DeviceDriver.startSynchronization() или DeviceDriver.connect().

Запуск и завершение синхронизации

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

Обработка подключения и отключения

Метод DeviceDriver.connect() должен установить соединения с оборудованием. Он обычно использует параметры связи, описанные в параграфе Установка Контекста Устройства (см выше). В большинстве случаев, установка соединения состоит из нескольких этапов:

  • Выборка параметров связи устройства посредством вызова getDeviceContext.getVariable(). Используйте getDeviceContext().getCallerController() в качестве контроллера вызова для обеспечения должного уровня прав доступа.
  • Создание подключения (открыть сокет TCP, серийный порт и пр.)
  • Отправка регистрационных данных авторизации/аутентификации и обработка ответа.
  • Переключение устройства на "режим конфигурации", если это применимо.

Метод connect()  должен сгенерировать исключение, если соединение прерывается на любом из этапов. В ином случае необходимо вызвать метод super.connect() в конце тела метода AbstractDeviceDriver, чтобы обозначить, что устройство подключено. AbstractDeviceDriver будет предоставлять результат для метода isConnected().

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

Чтобы зставить драйвер переподключиться во время тестирования/отладки драйвета, следует использовать действие Перезапустить драйвер устройства.

Чтение метаданных устройства

Существует три метода, вызываемые ядром SberMobile Serverа во время полной синхронизации:

  • readVariableDefinitions(), который должен проверять доступные настройки устройства (или свойства связи, если протокол устройства не поддерживает самодокументирование) и создавать объект VariableDefinition для каждой доступной настройки устройства. В зависимости от протокола связи, настройки  устройства могут также называться каналы ввода/вывода, тэги, записи настроек и пр. См. определение переменной.
  • readFunctionDefinitions(), который должен предоставлять по одному объекту FunctionDefinition для каждой операции, доступной для выполнения на устройстве. Для различных видов соединений согласно различным стандартам именования такие операции могут таже называться методами, функциями, действиями, процедурами, и т.д. См. определение функций.
  • readEventDefinitions(), который предоставляет по одному объекту EventDefinition для каждого типа события, которе может быть сгенерировано оборудованием. В некоторых протоколах устройств события могут также называться сообщениями, уведомлениями и пр. См. определение события.

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

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

Чтение/запись настроек устройства

Если драйвер предоставил непустой список настроек устройства из метода readVariableDefinitions(), ядро сервера вызовет метод драйвера readVariableValue() и writeVariableValue(). readVariableValue() должен прочитать последнее значение одной из настроек оборудования и преобразовать его в форму DataTable, соответствующую формату, определенному в его VariableDefinition. С другой стороны, writeVariableDefinition() принимает значение вида DataTable и конвертирует его в исходный формат, записывая переменную в устройство.

Настройки можно прочитать с оборудования:

  • во время первой синхронизации и
  • во время любой другой синхронизации, если на сервере их значения не изменились

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

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

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

Выполнение операций устройства

Если драйвер предоставил непустой список настроек устройства из метода readFuncitonDefinitions(), SberMobile Server добавит действие Вызвать функцию для каждой операции устройства. Выполняемое системным оператором, это действие запрашивает входные данные (согласно формату ввода функции, и только если он не "пустой"), а затем вызывает метод драйвера устройства executeFunction() и показывает его вывод оператору (также только если он не "пустой").

Таким образом, реализация ориентированного на драйвер метода executeFunction() должна:

  • конвертировать входные Таблицы Данных в исходный формат устройства
  • отправлять входные данные на оборудование
  • переключать операции устройства
  • читать вывод из устройства
  • конвертировать данные вывода в Таблицу Данных и возвращать их

Работа с событиями устройства

При оперировании событиями, драйвер устройства:

  • возвращает список определений событий из метода readEventDefinitions(). Список должен включать каждый тип события, который может производить аппаратное оборудование.
  • асинхронно вызывает метод DeviceContext.fireEvent(), когда новой экземпляр события получен из оборудования.

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

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

Любое событие, предоставляемое драйвером устройства, постоянно. Оно сохраняется в истории событий, если времени хранения истории не присвоено нулевое значение.

Расширенные свойства

См javadocs по DeviceDriver, DeviceContext и описание всех методов родительских интерфейсов.

Реинициализаторы параметров доступа

Если вы уже добавили несколько настроек связей, зависящих от девайсов (см. Создание Контекста Девайсов), вы можете выделить действия, которые будут вызываться, если эти настройки поменяются.

Чтобы сделать это, используйте DeviceContext.setAccessSettingReinitializer (String variable, AccessSettingReinitializer reinitializer). Метод реинициализатора reinitialize() будет вызываться каждый раз, когда предоставленная переменная изменяется. Реиниализатор может представлять действия, зависящие от девайсов. Его выход имеет булевское значение, которое показывает, требуется ли девайсу повторная синхронизация после изменения.