-
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
Fixes issue #175 retrying on Scan operation on error #174
Fixes issue #175 retrying on Scan operation on error #174
Conversation
fd1c0ee
to
5f7ba2e
Compare
5f7ba2e
to
cc1798f
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a strong +1 from me. I also faced the same issue today.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
After a discussion with @dariuszseweryn I have one more thing. Could you add some tests to the behaviour?
- Create an observable
- Disable bluetooth/loction services/ets.
- Try subscribing and see if there's an error
And the other way. Have the Bluetooth disabled, create an observable and then enable Bluetooth.
Sure @uKL . I will add it. |
Thanks a lot. Great job addressing this bug! :) 🥇 |
@uKL My pleasure! Thanks for this wonderful library :) Added a couple of tests. Let me know if I should change anything. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hello. Thank you for your contribution. What is needed are tests which will check that different results will be returned under different conditions. What I think is more like:
given:
// some condition is not met
def observable = objectUnderTest.scanBleDevices()
def testSubscriber0 = new TestSubscriber()
def testSubscriber1 = new TestSubscriber()
when:
observable.subscribe(testSubscriber0)
then:
testSubscriber.assertError...
// make the condition pass
when:
observable.subscribe(testSubscriber1)
then:
// check if the testSubscriber1 has no errors and everything else was called appropriately
Feel free to add tests that you think are feasible.
I will be happy to merge these changes when correct test cases will be implemented. :) 👍
bleAdapterWrapperSpy.hasBluetoothAdapter() >> true | ||
bleAdapterWrapperSpy.isBluetoothEnabled() >> false | ||
|
||
when: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
when:
should contain only one statement. In this situation scanObservable.subscribe(testSubscriber)
. The rest should go to given:
.
Besides – it is not possible to configure mocks and spies in when:
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@dariuszseweryn Will this approach be fine?
given:
TestSubscriber testSubscriber = new TestSubscriber<>()
bleAdapterWrapperSpy.hasBluetoothAdapter() >> true
bleAdapterWrapperSpy.isBluetoothEnabled() >> true
when:
def scanObservable = objectUnderTest.scanBleDevices(null)
then:
0 * bleAdapterWrapperSpy.isBluetoothEnabled()
when:
scanObservable.subscribe(testSubscriber)
then:
1 * bleAdapterWrapperSpy.startLeScan(_) >> true
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes
@dariuszseweryn Got it. I will make the necessary changes. |
Kindly check and let me know if anything is missing. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This one is better.
I think that we could use basically one well targeted test. Check review comments.
We are getting closer. :)
@@ -79,6 +79,49 @@ class RxBleClientTest extends Specification { | |||
1 * bleAdapterWrapperSpy.startLeScan(_) >> true | |||
} | |||
|
|||
def "should start BLE scan if bluetooth is enabled before subscribing to the scan observable"() { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This description does not seem to match the test. Here it is checking if bleAdapterWrapperSpy.isBluetoothEnabled()
was not called in line 92
1 * bleAdapterWrapperSpy.startLeScan(_) >> true | ||
} | ||
|
||
def "should start scan for only subscribers with no exceptions from scan observable"() { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Could you rephrase it to be easier to understand? Maybe something like: "should check if /condition/ is met at the time of each subscription"
It could like like this:
given:
def firstSubscriber = new TestSubscriber<>()
def secondSubscriber = new TestSubscriber<>()
bleAdapterWrapperSpy.hasBluetoothAdapter() >> true
bleAdapterWrapperSpy.startLeScan(_) >> true
def scanObservable = objectUnderTest.scanBleDevices(null)
when:
scanObservable.subscribe(firstSubscriber)
then:
1 * bleAdapterWrapperSpy.isBluetoothEnabled() >> false
and:
firstSubscriber.assertError {
BleScanException exception -> exception.reason == BLUETOOTH_DISABLED
}
when:
scanObservable.subscribe(secondSubscriber)
then:
1 * bleAdapterWrapperSpy.isBluetoothEnabled(_) >> true
and:
secondSubscriber.assertNoErrors()
Then we would need to make the test exercise for other conditions (isLocationPermissionOk
/ isLocationProviderOk
). It could be quite easily achieved by using where:
clause
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Got it. Do you think this would be fine using where:
?
def "should check if all the conditions are met at the time of each subscription"() {
given:
def firstSubscriber = new TestSubscriber<>()
def secondSubscriber = new TestSubscriber<>()
bleAdapterWrapperSpy.isBluetoothEnabled() >> bluetoothEnabled >> true
bleAdapterWrapperSpy.hasBluetoothAdapter() >> bluetoothAvailable >> true
locationServicesStatusMock.isLocationPermissionOk() >> locationPermissionsOk >> true
locationServicesStatusMock.isLocationProviderOk() >> locationProviderOk >> true
def scanObservable = objectUnderTest.scanBleDevices(null)
when:
scanObservable.subscribe(firstSubscriber)
then:
firstSubscriber.assertError {
BleScanException exception -> exception.reason == reason
}
when:
scanObservable.subscribe(secondSubscriber)
then:
secondSubscriber.assertNoErrors()
1 * bleAdapterWrapperSpy.startLeScan(_) >> true
where:
bluetoothAvailable | bluetoothEnabled | locationPermissionsOk | locationProviderOk | reason
false | true | true | true | BLUETOOTH_NOT_AVAILABLE
true | false | true | true | BLUETOOTH_DISABLED
true | true | false | true | LOCATION_PERMISSION_MISSING
true | true | true | false | LOCATION_SERVICES_DISABLED
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yup. That should do. We should have also the test that would first pass and then fail (the opposite scenario).
@@ -216,6 +259,21 @@ class RxBleClientTest extends Specification { | |||
} | |||
} | |||
|
|||
def "should emit BleScanException if bluetooth was disabled before starting scan"() { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This test is basically redundant to the one above and to the one at line 101
@@ -244,6 +302,21 @@ class RxBleClientTest extends Specification { | |||
} | |||
} | |||
|
|||
def "should emit BleScanException if location permission was not granted before starting scan"() { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
seems also to be redundant
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good for me. @uKL Feel free to comment.
@BharathMG Thank you for your support :) 👍 |
Dear Contributor, similar to many open source projects we kindly request to sign our CLA if you'd like to contribute to our project. This license is for your protection as a Contributor as well as the protection of Polidea; it does not change your rights to use your own Contributions for any other purpose. You can find a link here: https://cla-assistant.io/Polidea/RxAndroidBle |
Fixes scan never getting started when retrying on failed scan operation