Typescript - 在.subscribe()好的或坏的练习中调用另一个方法?

时间:2017-01-04 10:02:36

标签: angular typescript rxjs

这有效,但我有点紧张,因为我不确定它是不是一个黑客或好的做法。如果这是一个黑客或良好的做法,有人可以告诉我吗?

我这样做是为了确保第一个方法在启动第二个方法之前完全运行。

如果这是不好的做法,我相信请提供更好的方法来实施它。

我有一个方法调用HTTP GET方法,然后在subscribe中绑定它并调用另一个使用该数据调用另一个服务的方法。

 private bind(): void {

        this.Service.get(this.Id)
        .catch(this.logger.log)
        .subscribe(
        (customers: PersonalInfo[]) => { 

        this.customers = customers;               
                this.bindContactInfo();           
        }
        );
    }

private bindContactInfo():void{       

        this.Service.getContactInfo(this.Id)
        .catch(this.logger.log)
        .subscribe(   

        (contactInfo: ContactInformation[]) => {

         // stuff in here
        }
        );
        }  

1 个答案:

答案 0 :(得分:3)

一般情况下你可以这样做,我认为在服务中可以这样做,但是如果你的代码来自一个组件而且你要求“良好实践”,这里有一些选择:< / p>

选项1

您应该尝试避免手动订阅,使用.do(...)进行这类操作。同时尽量避免“硬链”,不能单独使用这些部件,因此请尝试将流分解为较小的部分,这样可以更容易地进行测试。考虑到这些要点,我会写这样的部分:

private getPersonalInfo(): Observable<PersonalInfo[]> {
    return this.Service.get(this.Id)
        .catch(this.logger.log)
        .do((customers: PersonalInfo[]) => this.customers = customers);
}

private getContactInfo(): Observable<ContactInformation[]> {
    return this.Service.getContactInfo(this.Id)
        .catch(this.logger.log)
        .do((contactInfo: ContactInformation[]) => this.contactInfo = contactInfo);
}

private getData(): void {
    this.getPersonalInfo()
        .switchMap(() => this.getContactInfo())
        .subscribe();
}

选项2

由于我假设你在一个组件中使用它,我会尽量避免像this.contactInfo = contactInfo这样的东西,并尝试在模板中使用| async(假设我只使用组件显示信息,不进行任何计算)

id$: ReplaySubject<string> = new ReplaySubject<string>(1); // this comes possibly from a service or from an @Input

personalInfo$: Observable<PersonalInfo[]> = this.id$
        .switchMap(id => this.Service.get(id))
        .catch(this.logger.log)
        .publishReplay(1)
        .refCount();

contactInfo$: Observable<ContactInformation[]> = this.id$  // or start it with this.personalInfo$.switchMapTo(this.id$) if you want to make sure that it is executed AFTER the personalInfo was fetched
        .switchMap(id => this.Service.get(id))
        .getContactInfo(this.Id)
        .catch(this.logger.log)
        .publishReplay(1)
        .refCount();

在您的模板中,您可以像这样使用它:

<div *ngFor="let personalInfo of personalInfo$ | async">
    ...
</div>

选项3

使用像ngrx这样的商店概念 - 这可能会导致很多重构。