1
votes

I got problem with zip operator. I plan to use timer observable

var timer = Observable<Int>
        .interval(0.1, scheduler: MainScheduler.instance)
        .do(onNext:
            { num in
                if(num == 20)
                {
                    //Purpose of this timer is to show progress if second request takes too long
                    MessagesManager.show_progress()
                }
        })

let source = Observable .... //my observable of networking request

return Observable.zip(source, timer,
               resultSelector: { value1, value2 in

                // Here i want to cancel/dispose/stop timer observable
                return value1
           })
    .do(onNext:
        { item in
            MessagesManager.dismiss_progress()
    }, onError:
        { error in
            MessagesManager.dismiss_progress()
    })

I expected zip operator to close second observable when first call onComplete, but timer continues to work after network request is completed. How can i solve this issue and dispose timer observable in/after zip block?

1

1 Answers

1
votes

Use take(1) to limit number of expected elements:

return Observable.zip(source, timer,
               resultSelector: { value1, value2 in
                return value1
           })
    .take(1)
    .do(onNext:
        { item in
            MessagesManager.dismiss_progress()
    }, onError:
        { error in
            MessagesManager.dismiss_progress()
    })

This way, after source emits first element, zip will create first pair of items. In your resultSelector you pick a first item from the pair and take(1) will make sure to complete (and then dispose) the observable right then.