I want to limit /test
API call to be called once in 3 seconds, so for instance:
2021-09-21 14:09:19.920 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.031 V/OkHttp: <-- 200 https://xxx/test (109ms)
2021-09-21 14:09:20.038 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.136 V/OkHttp: <-- 200 https://xxx/test (96ms)
2021-09-21 14:09:20.146 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.315 V/OkHttp: <-- 200 https://xxx/test (168ms)
2021-09-21 14:09:20.325 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.499 V/OkHttp: <-- 200 https://xxx/test (172ms)
2021-09-21 14:09:20.514 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.615 V/OkHttp: <-- 200 https://xxx/test (100ms)
2021-09-21 14:09:20.628 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.721 V/OkHttp: <-- 200 https://xxx/test (91ms)
2021-09-21 14:09:20.734 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.827 V/OkHttp: <-- 200 https://xxx/test (87ms)
Would be called once:
2021-09-21 14:09:19.920 V/OkHttp: --> GET https://xxx/test
2021-09-21 14:09:20.031 V/OkHttp: <-- 200 https://xxx/test (109ms)
For test purpose, I'm doing:
repeat(10) { index ->
apiRepo.test() //Returns Single
.toObservable()
.debounce(3, TimeUnit.SECONDS)
.subscribe({}, { Timber.e(it) })
}
I come from Coroutine world, so I think I've misunderstood how debounce
works, because I still get 10 calls (within 2 seconds), while I expect 1 in 3 seconds.
You create a new debounce
ten times. That is why it is not working as expected.
To achieve what you want you can use PublishSubject.
val apiCallSubject = PublishSubject.create<Unit>()
apiCallSubject
.debounce(3, TimeUnit.SECONDS)
.flatMapSingle { apiRepo.test() }
.subscribe({}, { Timber.e(it) })
repeat(10) { apiCallSubject.onNext(Unit) }
The point is that Observable which you debounce has to emit multiple items. In your case it is emitting only one but ten times.
You create new observable each iteration. Your apiRepo is returning new Observable
each time. You need to do something like this:
val publisher = PublishSubject.create<Unit>()
Observable.fromPublisher(publisher).debounce(3, TimeUnit.SECONDS).flatMap { api.testApi() }.subscribe({}, { Timber.e(it) })
repeat(1000000){
publisher.onNext(Unit)
}
From the loop you are emiting new items and as soon onNext()
is called, the chain will react upon it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With