-
Notifications
You must be signed in to change notification settings - Fork 589
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
RxBleRadioImpl is getting stuck after resetting Bluetooth #81
Comments
I've noticed the same exact input. The operations are queued even if you specified the operation with retryWhen() on the connection observable. |
To have more insight on this particular issue. I'll copy here the steps I'm doing to reproduce it: I have a class which is called BleDeviceManager: @Override public void connect(@NonNull final String address) {
rxBleDevice = rxBleClient.getBleDevice(address);
// Setup observation of connectivity changes
connectionStateSubscription = rxBleDevice.observeConnectionStateChanges().observeOn(AndroidSchedulers.mainThread()).subscribe(this::onConnectionStateChanged);
// Start properly the connection to the device
connectionObservable = rxBleDevice.establishConnection(context, false)
.takeUntil(disconnectionTrigger)
.retryWhen(this::onShouldRetryConnectionOperation)
.compose(new ConnectionSharingAdapter());
// Subscribe to the observable
connectionObservable.subscribe(this::onConnectionSuccess, this::onConnectionFailure);
}
private Observable<?> onShouldRetryConnectionOperation(Observable<? extends Throwable> observable) {
return observable.delay(RECONNECTION_DELAY_TIME, TimeUnit.SECONDS).filter(throwable -> {
if (throwable instanceof BleDisconnectedException) {
return true;
}
if (throwable instanceof BleGattException) {
BleGattException bleGattException = (BleGattException) throwable;
switch (bleGattException.getStatus()) {
case BLUEDROID_GATT_ERROR:
case BLUEDROID_GATT_CONNECTION_TIMEOUT:
return true;
}
}
return false;
});
}
private void onConnectionSuccess(RxBleConnection rxBleConnection) {
deviceSubscription = connectionObservable.observeOn(Schedulers.computation())
.flatMap(connection -> connection.discoverServices()
.flatMap(services -> services.getService(SERVICE_ID).map(BluetoothGattService::getCharacteristics)), Pair::with)
.flatMap(pair -> {
final RxBleConnection connection = pair.getValue0();
final List<BluetoothGattCharacteristic> characteristics = pair.getValue1();
return readInitialValues(connection, characteristics).concatWith(setupNotifications(connection, characteristics));
})
.subscribe(ignored -> {
}, throwable -> {
logger.e(TAG, "Error: " + throwable);
});
}
private Observable<Triplet<UUID, ValueAdapter<?>, byte[]>> readInitialValues(final RxBleConnection connection,
final List<BluetoothGattCharacteristic> characteristics) {
return Observable.from(characteristics)
.filter(characteristic -> BleUtils.hasReadProperty(characteristic.getProperties()))
.flatMap(connection::readCharacteristic, Pair::with)
.observeOn(Schedulers2.singleThread())
.compose(valueAdapterTransformer)
.doOnNext(triplet -> {
// Do things with the values received
});
}
private Observable<Triplet<UUID, ValueAdapter<?>, byte[]>> setupNotifications(final RxBleConnection connection,
final List<BluetoothGattCharacteristic> characteristics) {
return Observable.from(characteristics)
.filter(characteristic -> BleUtils.hasNotificationProperty(characteristic.getProperties()))
.flatMap(characteristic -> connection.setupNotification(characteristic).flatMap(observable -> observable), Pair::with)
.observeOn(Schedulers2.singleThread())
.compose(valueAdapterTransformer)
.doOnNext(triplet -> {
// Do things with the values received
});
} When I call the method This is the log I obtain:
This is the current state of the Is there a way to clear the queue? Or maybe to add a timeout to the operations? Thanks |
Hello. I was thinking about the problem. Actually it is not possible to cancel the current operation when it is executing because only establishing connection can be effectively cancelled. |
Hi @dariuszseweryn thanks for your comment! Is there any possibility that we can have a "hacky" solution meanwhile? Even if is not the most elegant one? (I would like to help you to sort this out). |
I am starting with writing tests for
at line 256 of |
Bad luck:
|
Another shot which theoretically should work:
where
I have quickly designed two test cases:
The first one passes and the second one fails with a somewhat funny message:
You can give it a shot - I do not have any Android device at the moment and can only test with unit tests. |
With this change, it looks very promising! For now, it does the reconnection properly!!! I'll tell you if I detect something wrong, testing more :) |
…connection happened before or during execution. Added some tests in RxBleGattCallbackTest. Summary: ( #81 ) (possibly also #76 ) Reviewers: michal.zielinski, pawel.urban Reviewed By: pawel.urban Differential Revision: https://phabricator.polidea.com/D1890
The above commit should fix the issue for good. In case of anything wrong - feel free to reopen the issue. Best Regards. |
Thanks @dariuszseweryn for your great work! Worth mentioning how fast you solved this thing! :) |
Reopening the issue as the fix introduced a different bug and was reverted. A proper fix is ready though it will wait till Monday for a code review. |
Can you share the new changes on the code? Or is already commited? I can test it on my device @dariuszseweryn Thanks!! :) |
…connection happened before or during execution. Added some tests in RxBleGattCallbackTest. Summary: ( #81 ) (possibly also #76 ) Reviewers: pawel.urban, michal.zielinski Differential Revision: https://phabricator.polidea.com/D1901
I have just pushed branch |
For now, working fine with my real device! 👍 |
…connection happened before or during execution. Added some tests in RxBleGattCallbackTest. Summary: ( #81 ) (possibly also #76 ) Reviewers: michal.zielinski, pawel.urban Reviewed By: pawel.urban Differential Revision: https://phabricator.polidea.com/D1904
Fix merged. Should be available in the SNAPSHOT. |
RxBleRadioImpl is getting stuck after resetting Bluetooth
Need connected app
Actual result
nothing happens, No connection
Expected result
Connection established
I can't see FINISHED after disabling bluetooth and also it's trying to write after disconnection:
10-14 17:44:02.136 2072-2931/ru.starline.key D/RxBle#Radio: QUEUED RxBleRadioOperationDisconnect(945209293)
10-14 17:44:02.136 2072-2133/ru.starline.key D/RxBle#Radio: STARTED RxBleRadioOperationDisconnect(945209293)
10-14 17:44:02.156 2072-2931/ru.starline.key D/RxBle#Radio: QUEUED RxBleRadioOperationDescriptorWrite(411833235)
10-14 17:44:02.166 2072-2133/ru.starline.key D/RxBle#Radio: FINISHED RxBleRadioOperationDisconnect(945209293)
10-14 17:44:02.166 2072-2133/ru.starline.key D/RxBle#Radio: STARTED RxBleRadioOperationDescriptorWrite(411833235)
10-14 17:44:02.166 2072-2931/ru.starline.key D/RxBle#Radio: QUEUED RxBleRadioOperationDescriptorWrite(840731593)
The text was updated successfully, but these errors were encountered: