RxJS捕获**并**重试Observable

RxJS catch **and** retry an Observable

本文关键字:Observable 重试 RxJS 捕获      更新时间:2023-09-26

我的用例是将Observable映射到成功和失败的redux操作。我进行一个网络调用(带有一个提供承诺的函数),如果成功,我必须转发一个成功操作,如果失败,则转发一个错误操作。观测者本身将继续前进。就我所能搜索到的而言,RxJS没有捕捉错误并重试原始错误的机制。我的代码中有以下我不满意的解决方案:

error$ = new Rx.Subject();
searchResultAction$ = search$
    .flatMap(getSearchResultsPromise)
    .map((resuls) => {
        return {
            type: 'SUCCESS_ACTION',
            payload: {
                results
            }
        }
    })
    .retryWhen((err$) => {
        return err$
            .pluck('query')
            .do(error$.onNext.bind(error$));
    });
searchErrorAction$
    .map((query) => {
        return {
            type: 'ERROR_ACTION',
            payload: {
                query,
                message: 'Error while retrieving data'
            }
        }
    });
action$ = Observable
    .merge(
        searchResultAction$,
        searchErrorAction$
    )
    .doOnError(err => console.error('Ignored error: ', err))
    .retry();
action$.subscribe(dispatch);

即,我创建一个主题,并将错误推到该主题中,并由此创建一个可观察的错误动作。

在RxJS中是否有我所缺少的更好的替代方法?基本上,我想发出一个发生错误的通知,然后继续Observable已经在做的事情。

这将重试失败的查询:

var action$ = search$
    .flatMap(value => {
        // create an observable that will execute
        // the query each time it is subscribed
        const query = Rx.Observable.defer(() => getSearchResultsPromise(value));
        // add a retry operation to this query
        return query.retryWhen(errors$ => errors$.do(err => {
            console.log("ignoring error: ", err);
        }));
    })
    .map(payload => ({ type: "SUCCESS_ACTION", payload }));
action$.subscribe(dispatcher);

如果您不想重试,只想通知或忽略错误:

var action$ = search$
    .flatMap(value => {
        // create an observable that will execute
        // the query each time it is subscribed
        const query = Rx.Observable.defer(() => getSearchResultsPromise(value));
        // add a catch clause to "ignore" the error
        return query.catch(err => {
            console.log("ignoring error: ", err);
            return Observable.empty(); // no result for this query
        }));
    })
    .map(payload => ({ type: "SUCCESS_ACTION", payload }));
action$.subscribe(dispatcher);