Reputation: 3162
Let's say I need to request a report from remote service. According to its API I need to do it in 3 steps: 1. Submit a request for report collecting(as a response I get reportId). 2. Check report status until it becomes 'done' with some delay(e.g. 10 seconds). 3. And finally get the report by id.
So, the question is following: is there any way using RxJava API check a predicate function until it returns true with some delay?
The most appropriate operator I could find was 'takeUntil' and code was something like this:
Observable.just(request)
.map(this::submitAndGetId)
.takeUntil(this::reportIsDone)
.map(this::getReport)
But I couldn't find a way to specify the delay between status checks
Upvotes: 1
Views: 1392
Reputation: 12087
Use flatMap
and interval
:
Observable
.just(request)
.map(this::submitAndGetId)
.flatMap(id ->
Observable
.interval(1, TimeUnit.SECONDS)
.filter(n -> reportIsDone(id))
.map(n -> id)
.first()
)
.map(this::getReport);
For a capped exponential backoff on the retries:
Observable<Long> retries =
Observable
.just(1, 2, 4, 8, 16)
.concatWith(Observable.just(30).repeat())
.flatMap(n -> Observable.timer(n, TimeUnit.SECONDS));
Observable
.just(request)
.map(this::submitAndGetId)
.flatMap(id ->
retries
.filter(n -> reportIsDone(id))
.map(n -> id)
.first()
)
.map(this::getReport);
Upvotes: 3