Rxjs 如何从失败的forkJoin请求中获取数据?
使用Rxjs 如何从失败的forkJoin请求中获取数据?,rxjs,ngrx,Rxjs,Ngrx,使用AngularRxjs和ngrx 我有一个调度4 API的操作,我正在执行以下操作=> @Effect() getAllModels$ = this.actions$.pipe( ofType<featureActions.GetAllModelsRequest>(featureActions.ActionTypes.GetAllModelsRequest), switchMap((action) => forkJoin([
Angular
Rxjs
和ngrx
我有一个调度4 API的操作,我正在执行以下操作=>
@Effect()
getAllModels$ = this.actions$.pipe(
ofType<featureActions.GetAllModelsRequest>(featureActions.ActionTypes.GetAllModelsRequest),
switchMap((action) =>
forkJoin([
this.dataService.GetAllModelFromServer(),
this.dataService.GetAllModelFromHost(),
this.dataService.GetAllModelFromCache(),
this.dataService.GetAllModelFromPreference(),
]).pipe(
map(
([server, host, cache, preference]) =>
new featureActions.GetAllModelsSuccess({
//...
})
),
catchError((error: HttpErrorResponse) => {
return of(new featureActions.GetAllModelsFailed({ error: error.message }));
})
)
)
);
@Effect()
getAllModels$=此.actions$.pipe(
类型(featureActions.ActionTypes.GetAllModelsRequest),
开关映射((操作)=>
分叉连接([
this.dataService.GetAllModelFromServer(),
this.dataService.GetAllModelFromHost(),
this.dataService.GetAllModelFromCache(),
this.dataService.GetAllModelFromPreference(),
]).烟斗(
地图(
([服务器、主机、缓存、首选项]=>
新功能Actions.GetAllModelsAccess({
//...
})
),
catchError((错误:HttpErrorResponse)=>{
返回(new featureActions.GetAllModelsFailed({error:error.message}));
})
)
)
);
问题是,当其中一个API失败时,一切都会失败,而我的行动也会失败。检索到的所有数据(在一个端点失败之前)都将丢失
有没有办法获取catchError中检索到的数据,或者唯一的解决方案是将api一个接一个地链接起来?您可以编写自己的
forkJoin
实现。下面是一个源于原始()的简单示例:
导出函数forkJoin2(…args:any[]):可观察{
const resultSelector=popsresultselector(args);
const{args:sources,key}=argsArgArrayOrObject(args);
如果(结果选择器){
//不推荐的路径。
返回forkJoinInternal(源、键).pipe(映射((值:any[])=>resultSelector!(…值));
}
返回内部(源、密钥);
}
函数forkJoinInternal(源:ObservableInput[],键:string[]| null):可观察{
返回新的可观察对象((订户)=>{
const len=sources.length;
如果(len==0){
subscriber.complete();
返回;
}
常量值=新数组(len);
设完成=0;
设发射=0;
for(让sourceIndex=0;sourceIndexerror:(err)=>{return subscriber.error({error:err,values})}
我在这里找到了这个解决方案:
@Effect()
getAllModels$=此.actions$.pipe(
类型(featureActions.ActionTypes.GetAllModelsRequest),
开关映射((操作)=>
分叉连接([
this.dataService.GetAllModelFromServer().pipe(catchError(()=>of({data:[]})),
this.dataService.GetAllModelFromHost().pipe(catchError(()=>of({data:[]})),
this.dataService.GetAllModelFromCache().pipe(catchError(()=>of({data:[]})),
this.dataService.GetAllModelFromPreference().pipe(catchError(()=>of({data:[]})),
]).烟斗(
地图(
([服务器、主机、缓存、首选项]=>
新功能Actions.GetAllModelsAccess({
//...
})
),
catchError((错误:HttpErrorResponse)=>{
返回(new featureActions.GetAllModelsFailed({error:error.message}));
})
)
)
);
你不能。除非您想编写自己的自定义“forkJoin”实现。i、 e.你可以调整这个:
export function forkJoin2(...args: any[]): Observable<any> {
const resultSelector = popResultSelector(args);
const { args: sources, keys } = argsArgArrayOrObject(args);
if (resultSelector) {
// deprecated path.
return forkJoinInternal(sources, keys).pipe(map((values: any[]) => resultSelector!(...values)));
}
return forkJoinInternal(sources, keys);
}
function forkJoinInternal(sources: ObservableInput<any>[], keys: string[] | null): Observable<any> {
return new Observable((subscriber) => {
const len = sources.length;
if (len === 0) {
subscriber.complete();
return;
}
const values = new Array(len);
let completed = 0;
let emitted = 0;
for (let sourceIndex = 0; sourceIndex < len; sourceIndex++) {
const source = innerFrom(sources[sourceIndex]);
let hasValue = false;
subscriber.add(
source.subscribe({
next: (value) => {
if (!hasValue) {
hasValue = true;
emitted++;
}
values[sourceIndex] = value;
},
error: (err) => { return subscriber.error({ error: err, values }) },
complete: () => {
completed++;
if (completed === len || !hasValue) {
if (emitted === len) {
subscriber.next(keys ? keys.reduce((result, key, i) => (((result as any)[key] = values[i]), result), {}) : values);
}
subscriber.complete();
}
},
})
);
}
});
}
@Effect()
getAllModels$ = this.actions$.pipe(
ofType<featureActions.GetAllModelsRequest>(featureActions.ActionTypes.GetAllModelsRequest),
switchMap((action) =>
forkJoin([
this.dataService.GetAllModelFromServer().pipe(catchError(() => of({ data: [] }))),
this.dataService.GetAllModelFromHost().pipe(catchError(() => of({ data: [] }))),
this.dataService.GetAllModelFromCache().pipe(catchError(() => of({ data: [] }))),
this.dataService.GetAllModelFromPreference().pipe(catchError(() => of({ data: [] }))),
]).pipe(
map(
([server, host, cache, preference]) =>
new featureActions.GetAllModelsSuccess({
//...
})
),
catchError((error: HttpErrorResponse) => {
return of(new featureActions.GetAllModelsFailed({ error: error.message }));
})
)
)
);