All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.github.davidmoten.rx.internal.operators.TransformerOnTerminateResume Maven / Gradle / Ivy

package com.github.davidmoten.rx.internal.operators;

import rx.*;
import rx.Observable.*;
import rx.exceptions.*;
import rx.functions.Func1;
import rx.internal.producers.ProducerArbiter;

/**
 * Switches to different Observables if the main source completes or signals an error.
 *
 * @param  the value type
 */
public final class TransformerOnTerminateResume implements Transformer {
    
    final Func1> onError;
    
    final Observable onCompleted;

    public TransformerOnTerminateResume(Func1> onError, Observable onCompleted) {
        this.onError = onError;
        this.onCompleted = onCompleted;
    }

    @Override
    public Observable call(final Observable o) {
        return Observable.create(new OnSubscribe() {
            @Override
            public void call(Subscriber t) {
                OnTerminateResumeSubscriber parent = new OnTerminateResumeSubscriber(t, onError, onCompleted);
                
                t.add(parent);
                t.setProducer(parent.arbiter);
                
                o.unsafeSubscribe(parent);
            }
        });
    }
    
    static final class OnTerminateResumeSubscriber extends Subscriber {

        final Subscriber actual;
        
        final Func1> onError;
        
        final Observable onCompleted;

        final ProducerArbiter arbiter;
        
        long produced;
        
        public OnTerminateResumeSubscriber(Subscriber actual, Func1> onError,
                Observable onCompleted) {
            this.arbiter = new ProducerArbiter();
            this.actual = actual;
            this.onError = onError;
            this.onCompleted = onCompleted;
        }

        @Override
        public void onNext(T t) {
            produced++;
            actual.onNext(t);
        }

        @Override
        public void onError(Throwable e) {
            long p = produced;
            if (p != 0L) {
                arbiter.produced(p);
            }
            
            Observable o;
            
            try {
                o = onError.call(e);
            } catch (Throwable ex) {
                Exceptions.throwIfFatal(ex);
                
                actual.onError(new CompositeException(e, ex));
                
                return;
            }
            
            if (o == null) {
                actual.onError(new NullPointerException("The onError function returned a null Observable."));
            } else {
                o.unsafeSubscribe(new ResumeSubscriber(actual, arbiter));
            }
        }

        @Override
        public void onCompleted() {
            long p = produced;
            if (p != 0L) {
                arbiter.produced(p);
            }
            onCompleted.unsafeSubscribe(new ResumeSubscriber(actual, arbiter));
        }
        
        @Override
        public void setProducer(Producer p) {
            arbiter.setProducer(p);
        }
        
        static final class ResumeSubscriber extends Subscriber {
            final Subscriber actual;
            
            final ProducerArbiter arbiter;

            public ResumeSubscriber(Subscriber actual, ProducerArbiter arbiter) {
                this.actual = actual;
                this.arbiter = arbiter;
            }

            @Override
            public void onCompleted() {
                actual.onCompleted();
            }

            @Override
            public void onError(Throwable e) {
                actual.onError(e);
            }

            @Override
            public void onNext(T t) {
                actual.onNext(t);
            }

            @Override
            public void setProducer(Producer p) {
                arbiter.setProducer(p);
            }
        }
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy