0

I have a little problem with subscribing my Observable

I have one one combined Observable:

private selectedEntryId$ = new Subject<number>();
private entries$ = new Subject<MappingEntry[]>();

private selectedEntry$ = Observable.combineLatest(
    this.entries$,
    this.selectedEntryId$,
    (entries: MappingEntry[], id: number) => {
        return entries.find((entry: MappingEntry) => {
            return entry.id === id;
        });
    });

I try do API call every time, when my selectedEntry$ has next value and subscribe result in this way:

constructor(private checkService: CheckService) {
    this.subscribeLengthCalculator();
}

subscribeLengthCalculator() {
    this.subscriptions.add(
        this.selectedEntry$
            .switchMap((entry) => {
                return entry ? this.checkService.calculateLinesLength([entry.value]) : Observable.empty();
            }).subscribe(([calculation: CalculationObject]) => {
                    console.log(calculation);
                    this.calculation = calculation;
             })
    );
}

First time when selectedEntry$ has next value, console.log throw to the console correct API result, but in my html calculation has null value. When selectedEntry$ has second next value, console.log throw to the console correct API result too but in html show mi previous value. Anyone can explain me this behaviour and tell me what I should do to showing current data in html? It's very strange behaviour.

4

1 回答 1

0

引用learnrxjs “不过要小心,您可能希望避免switchMap在每个请求都需要完成的情况下”。

“与其他展平运算符的主要区别在于switchMap取消效果”,这就是为什么当selectedEntry$有第二个下一个值时,它会显示您之前的值。源 observable ( this.selectedEntry$) a;ready 完成,订阅仅对Observable来自此行的消息有效:

return entry ? this.checkService.calculateLinesLength([entry.value]) : Observable.empty()

因此,话虽如此,我建议您尝试concatMap而不是switchMap

subscribeLengthCalculator() {
    this.subscriptions.add(
        this.selectedEntry$
            .concatMap((entry) => {
                return entry ? this.checkService.calculateLinesLength([entry.value]) : Observable.empty();
            }).subscribe(([calculation: CalculationObject]) => {
                    console.log(calculation);
                    this.calculation = calculation;
             })
    );
}

但事实上,我喜欢管道运营商,所以答案是:

import { concatMap } from 'rxjs/observable/concatMap';

subscribeLengthCalculator() {
        this.subscriptions.add(
            this.selectedEntry$
                .pipe(
                    concatMap((entry) => {
                        return entry ? this.checkService.calculateLinesLength([entry.value]) : Observable.empty();
                    })
                ).subscribe(([calculation: CalculationObject]) => {
                    console.log(calculation);
                    this.calculation = calculation;
                })
        );
    }
于 2018-05-24T22:14:23.253 回答