У меня есть логика повторного подключения BLE c, которая сначала извлекает подключенное устройство, используя указанный c сервисный UUID, если не найден, а затем извлекает предыдущее подключенное устройство с сохраненным периферийным UUID. Если периферийный UUID не найден, центральный менеджер будет сканировать и обнаруживать с тем же UUID службы. Однако сканирование работает, и центральный менеджер может обнаружить периферийное устройство. Но если инициировать переподключение из приложения, и в этом случае BLE все еще подключен на уровне ОС (отображается как подключенный в настройках iOS BT), central.retrieveConnectedPeripherals (withServices: [SERVICE_UUID]) ничего не возвращает.
Есть ли что-то, чего мне не хватает для создания central.retrieveConnectedPeripherals (withServices: [SERVICE_UUID]) возвращает подключенные периферийные устройства с SERVICE_UUID?
Вот соответствующий код:
// master function to control the connection logic
private func connect(with peripheralIdentifier: String) {
// connectedPeripheral is always nil even when BLE is connected on OS level
if let connectedPeripheral = retrieveConnectedPeripheral(forIdentifier: peripheralIdentifier) {
logger.d("peripheral is already connected in OS, establishing local connection...")
self.peripheral = peripheral
central.connect(connectedPeripheral, options: nil)
return
}
if let peripheral = retrievePeripheral(forIdentifier: peripheralIdentifier) {
logger.d("peripheral was previous connected, attempting to reconnect...")
self.peripheral = peripheral
central.connect(peripheral, options: nil)
return
}
// start scan only when peripheral was never connected
startPairing()
}
private func retrieveConnectedPeripheral(forIdentifier uuid: String) -> CBPeripheral? {
return central
.retrieveConnectedPeripherals(withServices: [SERVICE_UUID])
.first
}
private func retrievePeripheral(forIdentifier uuid: String) -> CBPeripheral? {
let p = central.retrievePeripherals(withIdentifiers: [uuid]).first
logger.d("retrieved peripheral has services \(p?.services)") // it's always [], even when peripheral.discoverServices is called in didConnect callback
return p
}
private func startPairing() {
central.scanForPeripherals(
withServices: [
SERVICE_UUID
],
options: nil)
}
func centralManager(_ central: CBCentralManager,
didDiscover peripheral: CBPeripheral,
advertisementData: [String: Any],
rssi RSSI: NSNumber) {
if foundPeripheral(peripheral.name) {
logger.d("""
discovered a matching peripheral with \(String(describing: peripheral.name)),
UUID \(peripheral.identifier),
advertisementData \(advertisementData.description)
""")
self.peripheral = peripheral
self.central.connect(peripheral, options: nil)
}
}
func centralManager(_ central: CBCentralManager,
didConnect peripheral: CBPeripheral) {
let uuid = peripheral.identifier
// stores the UUID for reconnection
setPeripheralUuid(forKey: identifier, uuid: uuid)
peripheral.delegate = self
// calling this because the Developer Doc says without this, peripheral.services will be []. But after calling this, it's still []
peripheral.discoverServices([SERVICE_UUID])
stopScan()
}
func peripheral(_ peripheral: CBPeripheral, didDiscoverServices error: Error?) {
if error == nil {
logger.d("discovered services: \(peripheral.services)") // falls into this case, but it's []
} else {
logger.e("Failed to discover service for \(peripheral)!", error)
}
}
Как упомянуто в комментарии к коду, не уверен, что central.retrieveConnectedPeripherals (withServices: [SERVICE_UUID]) ничего не возвращает, связанный с периферийным устройством. ничего не возвращает. Вполне возможно, что есть что-то очевидное, что мне не хватает t