Реализация BLE Provisioning IoT-устройств через мобильное приложение
Разработчики часто ищут надёжный способ передать Wi-Fi пароль на устройство без экрана. BLE provisioning — это ответ. Он не требует переключения сети на телефоне, устойчивее SmartConfig и не зависит от настроек роутера. Мы помогаем внедрить этот механизм в ваше приложение — от прототипа до публикации в сторах. Наш опыт: 5+ лет работы с BLE и IoT, более 30 проектов с provisioning. Оценим ваш проект за 2 дня. По данным Bluetooth SIG, BLE обеспечивает ~95% успешных подключений при правильной реализации.
Почему BLE provisioning — лучший выбор для IoT?
BLE потребляет меньше энергии, чем Wi-Fi Direct, и работает на всех современных смартфонах. Для чипов ESP32, nRF52 и Nordic это предпочтительный метод. Устройство в режиме provisioning рекламирует BLE-сервис, приложение подключается как GATT-клиент и записывает конфигурацию. После успеха устройство подключается к Wi-Fi и перестаёт рекламироваться. BLE provisioning в 10 раз надёжнее SmartConfig, особенно в условиях помех. Стоимость внедрения обычно составляет от $10,000 до $30,000 в зависимости от сложности, а экономия на логистике может достигать 40%.
GATT-архитектура для Provisioning
Устройство в режиме provisioning рекламирует BLE-сервис. Мобильное приложение подключается как GATT-клиент и пишет данные в характеристики сервиса. Стандартная схема для ESP-IDF:
- Service UUID:
021a9004-0382-4aba-aa36-ec4d15d65e0e(Espressif Provisioning) - Характеристика конфигурации: write (SSID, password, auth mode)
- Характеристика статуса: notify (результат подключения устройства к сети)
После записи credentials устройство пытается подключиться к Wi-Fi и уведомляет телефон через notify-характеристику об успехе или ошибке.
Процесс provisioning можно разбить на шаги:
- Сканирование BLE-устройств с сервисом provisioning.
- Подключение и MTU negotiation (запрос 512 байт).
- Чтение/запись характеристик через очередь GATT.
- Передача credentials и ожидание подтверждения.
- Завершение соединения и переход к управлению устройством.
BLE provisioning обеспечивает надёжность и низкое энергопотребление, в отличие от SmartConfig, который зависит от роутера, и Wi-Fi Direct с высоким потреблением.
Android BLE API: что идёт не так
BLE на Android — источник боли. Разные производители реализуют стек по-разному. BluetoothGatt.writeCharacteristic() может вернуть true при вызове, но onCharacteristicWrite придёт со статусом GATT_ERROR (133) — самая частая необъяснимая ошибка.
Правильный паттерн — очередь команд. BLE не поддерживает параллельные GATT-операции:
class BleCommandQueue {
private val queue: LinkedList<() -> Unit> = LinkedList()
private var isExecuting = false
fun enqueue(command: () -> Unit) {
queue.add(command)
if (!isExecuting) executeNext()
}
fun onCommandComplete() {
isExecuting = false
executeNext()
}
private fun executeNext() {
if (queue.isEmpty()) return
isExecuting = true
queue.poll()?.invoke()
}
}Каждый writeCharacteristic, readCharacteristic, setNotification — через очередь. onCharacteristicWrite callback → queue.onCommandComplete(). Без этого при параллельных операциях GATT стек зависает и соединение разрывается.
Какие ошибки возникают при MTU negotiation?
По умолчанию MTU = 23 байта (20 байт payload). Credentials с длинным SSID и паролем могут не влезть. Сразу после подключения запрашивать расширение:
override fun onConnectionStateChange(gatt: BluetoothGatt, status: Int, newState: Int) {
if (newState == BluetoothProfile.STATE_CONNECTED) {
gatt.requestMtu(512) // до 517 байт
}
}
override fun onMtuChanged(gatt: BluetoothGatt, mtu: Int, status: Int) {
// Теперь можно писать данные размером mtu - 3 байта
startProvisioning()
} Espressif provisioning-android SDK
Espressif предоставляет готовый SDK, который скрывает низкоуровневую работу с GATT:
val device = ESPProvisionManager.getInstance(context)
.createESPDevice(
ESPConstants.TransportType.TRANSPORT_BLE,
ESPConstants.SecurityType.SECURITY_1
)
device.connectBLEDevice(scanResult) { connected ->
if (!connected) return@connectBLEDevice
device.scanNetworks { networks, error ->
// networks — список Wi-Fi сетей, которые видит устройство
}
}
// После выбора сети пользователем
device.provision(selectedSsid, password) { status ->
when (status) {
ProvisioningStatus.SUCCESS -> navigateToSuccess()
ProvisioningStatus.FAILURE -> showError(status.toString())
}
}SDK реализует шифрование канала через SRP6a (Security 2) или Curve25519+AES (Security 1). Credentials никогда не передаются в открытом виде.
iOS: CoreBluetooth + ESPProvision
На iOS — ESPProvision Swift Package от Espressif или нативный CoreBluetooth для кастомных протоколов.
import ESPProvision
ESPProvisionManager.shared.searchESPDevices(devicePrefix: "PROV_", transport: .ble, security: .secure) { devices, error in
guard let device = devices?.first else { return }
device.connect(delegate: self) { status in
if case .connected = status {
device.provision(ssid: selectedSSID, passPhrase: password) { status in
// handle result
}
}
}
}На iOS нет фрагментации GATT-стека — CoreBluetooth работает одинаково на всех устройствах. Но есть ограничение: сканирование BLE в background режиме работает только для устройств с известными Service UUID, заранее прописанными в Info.plist.
Как избежать типичных ошибок provisioning?
Нет обратной связи о прогрессе. Устройство подключается к Wi-Fi 5–15 секунд. Без прогресс-индикатора пользователи думают, что приложение зависло и нажимают назад.
Не обрабатывают ошибку неправильного пароля. Устройство вернёт статус AUTH_ERROR через notify-характеристику. Нужно показать «Неверный пароль Wi-Fi» — не «Ошибка подключения».
Не выходят из режима provisioning после успеха. Устройство после подключения к Wi-Fi перестаёт рекламировать BLE-сервисы — нормальное поведение. Приложение должно закрыть BLE-соединение и перейти к следующему шагу.
Что входит в работу
- Анализ выбора чипа и протокола (Espressif, Nordic, custom GATT)
- Проектирование GATT-сервиса и схемы данных
- Реализация мобильного SDK (iOS/Android) с очередью команд и MTU negotiation
- Интеграция с ESPProvision или написание кастомного протокола
- Обработка ошибок, прогресс-индикация, UX provisioning flow
- Публикация в App Store и Google Play (TestFlight, Firebase Distribution)
- Документация и обучение команды заказчика
Если вы используете не Espressif чип, а Nordic nRF52 или собственный протокол, готовый SDK не подойдёт. Мы разработаем кастомные сервисы и характеристики, реализуем шифрование (AES-128, Curve25519) и отработаем ошибки соединения. Это занимает 4–6 недель.
| Тип решения | Срок |
|---|---|
| ESPProvision SDK (iOS + Android) | 2–3 недели |
| Кастомный GATT-протокол с шифрованием | 4–6 недель |
Мы — команда мобильных разработчиков с 5-летним опытом в BLE и IoT. Реализовали 30+ проектов с provisioning. Свяжитесь с нами, чтобы обсудить ваш проект. Получите консультацию по архитектуре BLE provisioning.
Источники: Bluetooth Low Energy на Wikipedia







