Связь между устройством BLE и различными приложениями Android на одном устройстве - PullRequest
0 голосов
/ 03 мая 2018

Я новичок в Android BLE, поэтому мой вопрос может быть неправильным или наивным в некотором роде. Если это так, пожалуйста, объясните мне, где я ошибаюсь, и, пожалуйста, покажите мне правильный способ управления этим сценарием.

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

Последовательность:

  • Устройство запускает приложение (вызывается метод onConnectionStateChange)
  • Мое приложение записывает команду в характеристике (я называю writeCharacteristic, помещая команду в параметр value).
  • Устройство отправляет ответ на команду в мое приложение (метод onCharacteristicChanged запущен, а параметр value содержит ответ)

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

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

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

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

Есть ли способ для приложения установить канал связи с устройством BLE, чтобы избежать отправки ответа на конкретные команды любому другому приложению, кроме того, которое отправило запрос?

Я предполагаю, что writeCharacteristic и onNotificationChanged не являются правильными функциями для такого рода коммуникации, но в этом случае, какие альтернативы?

1 Ответ

0 голосов
/ 04 мая 2018

Сам по себе стандарт Bluetooth ничего не определяет, как будут вести себя несколько приложений, если оба будут подключены к одному устройству GATT. В стандарте есть только один «клиент ГАТТ».

Теперь и iOS, и Android сделали еще один шаг вперед, что может показаться не интуитивным. Вместо того, чтобы разрешать связь только одному приложению за раз, несколько приложений могут быть подключены через устройство к одному клиенту GATT. ОС "мультиплексирует" связь между приложениями и приложениями. Поведение заключается в том, что ответы на запросы на чтение и запись могут видеть только приложение, сделавшее запрос. Поэтому, если вы выполните readCharacteristic, только это приложение получит обратный вызов onCharacteristicRead. Однако уведомления будут доставляться обоим приложениям на обратный вызов onCharacteristicChanged, поскольку отправлять уведомления только одному не имеет смысла.

Когда вы говорите, что «ответ» на запрос на запись является уведомлением, это неверно с точки зрения терминологии ГАТТ. Ответ на запрос записи всегда пуст для каждой спецификации (или ошибки). Если ваше периферийное устройство отправляет уведомление, то в вашем случае это может быть «ответ» в соответствии с вашей собственной логикой, но это не ответ или какое-либо отношение к вашему запросу на запись согласно спецификации GATT. Вот почему Android не может (и не должен) отправлять уведомления только на одно устройство.

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

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

...