Compare commits
2 commits
e9b668cb20
...
34e8ea0bab
| Author | SHA1 | Date | |
|---|---|---|---|
| 34e8ea0bab | |||
| df6601c50b |
1 changed files with 37 additions and 2 deletions
|
|
@ -179,8 +179,10 @@ class BeaconProvisioner: NSObject, ObservableObject {
|
|||
// Connection retry state
|
||||
private var connectionRetryCount = 0
|
||||
private var deviceInfoRetryCount = 0
|
||||
private var disconnectRetryCount = 0
|
||||
private static let MAX_CONNECTION_RETRIES = 3
|
||||
private static let MAX_DEVICE_INFO_RETRIES = 2
|
||||
private static let MAX_DISCONNECT_RETRIES = 2
|
||||
private var currentBeacon: DiscoveredBeacon?
|
||||
|
||||
override init() {
|
||||
|
|
@ -222,6 +224,7 @@ class BeaconProvisioner: NSObject, ObservableObject {
|
|||
self.isTerminating = false
|
||||
self.connectionRetryCount = 0
|
||||
self.deviceInfoRetryCount = 0
|
||||
self.disconnectRetryCount = 0
|
||||
self.currentBeacon = beacon
|
||||
|
||||
state = .connecting
|
||||
|
|
@ -270,6 +273,7 @@ class BeaconProvisioner: NSObject, ObservableObject {
|
|||
self.allDiscoveredServices.removeAll()
|
||||
self.connectionRetryCount = 0
|
||||
self.deviceInfoRetryCount = 0
|
||||
self.disconnectRetryCount = 0
|
||||
self.isTerminating = false
|
||||
self.currentBeacon = beacon
|
||||
self.servicesToExplore.removeAll()
|
||||
|
|
@ -308,6 +312,7 @@ class BeaconProvisioner: NSObject, ObservableObject {
|
|||
isTerminating = false
|
||||
connectionRetryCount = 0
|
||||
deviceInfoRetryCount = 0
|
||||
disconnectRetryCount = 0
|
||||
currentBeacon = nil
|
||||
state = .idle
|
||||
progress = ""
|
||||
|
|
@ -888,6 +893,7 @@ class BeaconProvisioner: NSObject, ObservableObject {
|
|||
characteristics.removeAll()
|
||||
connectionRetryCount = 0
|
||||
deviceInfoRetryCount = 0
|
||||
disconnectRetryCount = 0
|
||||
currentBeacon = nil
|
||||
operationMode = .provisioning
|
||||
state = .idle
|
||||
|
|
@ -1019,6 +1025,7 @@ extension BeaconProvisioner: CBCentralManagerDelegate {
|
|||
dxSmartNotifySubscribed = false
|
||||
dxSmartCommandQueue.removeAll()
|
||||
dxSmartWriteIndex = 0
|
||||
passwordIndex = 0
|
||||
characteristics.removeAll()
|
||||
responseBuffer.removeAll()
|
||||
state = .connecting
|
||||
|
|
@ -1034,8 +1041,36 @@ extension BeaconProvisioner: CBCentralManagerDelegate {
|
|||
return
|
||||
}
|
||||
|
||||
// All other disconnects are unexpected
|
||||
DebugLog.shared.log("BLE: UNEXPECTED disconnect — state=\(state) writeIdx=\(dxSmartWriteIndex) queueCount=\(dxSmartCommandQueue.count) authenticated=\(dxSmartAuthenticated)")
|
||||
// Unexpected disconnect during auth or writing — retry with full reconnect
|
||||
if (state == .authenticating || state == .writing) && disconnectRetryCount < BeaconProvisioner.MAX_DISCONNECT_RETRIES {
|
||||
disconnectRetryCount += 1
|
||||
DebugLog.shared.log("BLE: Disconnect during \(state) — reconnecting (attempt \(disconnectRetryCount)/\(BeaconProvisioner.MAX_DISCONNECT_RETRIES))")
|
||||
progress = "Beacon disconnected, reconnecting (\(disconnectRetryCount)/\(BeaconProvisioner.MAX_DISCONNECT_RETRIES))..."
|
||||
|
||||
// Reset connection state for clean reconnect
|
||||
dxSmartAuthenticated = false
|
||||
dxSmartNotifySubscribed = false
|
||||
dxSmartCommandQueue.removeAll()
|
||||
dxSmartWriteIndex = 0
|
||||
passwordIndex = 0
|
||||
characteristics.removeAll()
|
||||
responseBuffer.removeAll()
|
||||
state = .connecting
|
||||
|
||||
let delay = Double(disconnectRetryCount) + 1.0 // 2s, 3s backoff
|
||||
DispatchQueue.main.asyncAfter(deadline: .now() + delay) { [weak self] in
|
||||
guard let self = self, let beacon = self.currentBeacon else { return }
|
||||
guard self.state == .connecting else { return }
|
||||
let resolvedPeripheral = self.resolvePeripheral(beacon)
|
||||
self.peripheral = resolvedPeripheral
|
||||
resolvedPeripheral.delegate = self
|
||||
self.centralManager.connect(resolvedPeripheral, options: nil)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
// All retries exhausted or disconnect in unexpected state — fail
|
||||
DebugLog.shared.log("BLE: UNEXPECTED disconnect — state=\(state) writeIdx=\(dxSmartWriteIndex) queueCount=\(dxSmartCommandQueue.count) authenticated=\(dxSmartAuthenticated) disconnectRetries=\(disconnectRetryCount)")
|
||||
fail("Unexpected disconnect (state: \(state))", code: .disconnected)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue