Error Handling

Reading about error handling in programming, seems like a good

JavaScript Error Handling

Observable Error


        rxjs.of('test', 'test error')
        .pipe(
            rxjs.operators.map(str => {
                if(str.includes(' ')) {
                    throw new Error(`Error trailing space: ${str}`)
                }
                return str;
            })
        )
        .subscribe(
            (res) => console.log(res),
            (err) => console.log(`[Error]: ${err}`),
            () => console.log('Observable completed!')
        )
    
Schema Observale error

CatchError Operator


        rxjs.of(2,3,4,6)
        .pipe(
            rxjs.operators.map(num => {
                if(num % 2 !== 0) {
                throw new Error(`Unexpected odd number: ${num}`)
                }
                return num;
            }),
            rxjs.operators.catchError(err => rxjs.of(0)),
            rxjs.operators.map(num => ++num)
        )

        .subscribe(
            (res) => console.log(res),
            (err) => console.log(`[Error]: ${err}`),
            () => console.log('Observable completed!')
        )
    
Schema catch Observable Operator
Catches errors on the observable to be handled by returning a new observable or throwing an error

Retry Operator


        rxjs.of(2,3,4,6)
        .pipe(
            rxjs.operators.map(num => {
                if(num % 2 !== 0) {
                throw new Error(`Unexpected odd number: ${num}`)
                }
                return num;
            }),
            rxjs.operators.map(num => ++num)
            rxjs.operators.catchError((err) => rxjs.of(0))

        )

        .subscribe(
            (res) => console.log(res),
            (err) => console.log(`Caught: ${err}`),
            () => console.log('Observable completed!')
        )
    
Returns an Observable that mirrors the source Observable with the exception of an error.
If the source Observable calls error, this method will resubscribe to the source Observable for a maximum of count resubscriptions (given as a number parameter) rather than propagating the error call

Promise Immutability


        mySource$
            .pipe(
                rxjs.operators.switchMap((url) => callPromise(url)),
                rxjs.operators.retry(3)
            )
    

Backoff strategy

RetryWhen Operator


        // linear backoff strategy
        .pipe(rxjs.operators.retryWhen(errors$ =>
            rxjs.range(1, maxRetries)
                .pipe(
                    rxjs.operators.zip(errors$, (i, err) => ({'i': i, 'err': err})),
                    rxjs.operators.mergeMap(({i, err}) =>
                        Rx.Observable.if(() => i <= maxRetries - 1,
                            rxjs.timer(i * 1000)
                                .pipe(rxjs.operators.tap(() => console.log(`Retrying after ${i} second(s)...`))),
                            rxjs.throw(err))
                    )
                )

        )
    
Schema retryWhen Observable Operator
Returns an Observable that mirrors the source Observable with the exception of an error.
If the source Observable calls error, this method will emit the Throwable that caused the error to the Observable returned from notifier. If that Observable calls complete or error then this method will call complete or error on the child subscription. Otherwise this method will resubscribe to the source Observable.

Replay vs Subscribe

Replay the same stream in other words keep the same side effect value Whereas, subscribe regenerate a new sequence => Promise example

Finalize Operator


        const source$ = rxjs.of(1,2,3,4,5)
        .finalize(() => console.log('FINALIZE'))

        .subscribe(
            (res) => console.log(res),
            (err) => console.log(`[Error]: ${err}`),
            () => console.log('Observable completed!')
        )
    
Returns an Observable that mirrors the source Observable, but will call a specified function when the source terminates on complete or error