zoukankan      html  css  js  c++  java
  • [RxJS] Reactive pattern: Passing Observable and trigger side effect until it complete

    For example, we want to show loading spinner inside our appliction component trees. Because we might trigger loading spinner anywhere inside our application, therefore, we need to use a loading.service.ts to communciate between different compnents.

    loading.service.ts:

    import {Injectable} from '@angular/core';
    import {BehaviorSubject, Observable, of} from 'rxjs';
    import {concatMap, finalize, tap} from 'rxjs/operators';
    
    @Injectable()
    export class LoadingService {
    
      private loadingSubject = new BehaviorSubject<boolean>(false);
    
      loading$: Observable<boolean> = this.loadingSubject.asObservable();
    
      loadingOn() {
        this.loadingSubject.next(true);
      }
    
      loadingOff() {
        this.loadingSubject.next(false);
      }
    
      showLoaderUntilCompleted<T>(obs$: Observable<T>): Observable<T> {
        return of(null)
          .pipe(
            tap(() => this.loadingSubject.next(true)),
            concatMap(() => obs$),
            finalize(() => {
              this.loadingSubject.next(false);
            })
          );
      }
    }

    Component:

    import { Component, OnInit } from '@angular/core';
    import {Observable} from 'rxjs';
    import {LoadingService} from './loading.service';
    
    @Component({
      selector: 'loading',
      template: '<div class="spinner-container" *ngIf="loading$ | async"><mat-spinner></mat-spinner></div>'
    })
    export class LoadingComponent implements OnInit {
    
      loading$ : Observable<boolean>;
      constructor(private loadingService: LoadingService) {
    
      }
    
      ngOnInit() {
    
        this.loading$ = this.loadingService.loading$;
      }
    }

    The most important thing to understand here is the function: showLoaderUntilComplete(obs$). 

    It takes a Observable, because we want to wait 'obs$' to complete, therefore, we use 'concatMap', it executes observable one by one, then we use 'finalize' operator, it will execute callback function when the observable completes. Here means waiting 'obs$' to be completed.

    How to use it?

    courses.service.ts

    private subject = new BehaviorSubject<Course[]>([]);
    
    courses$ = this.subject.asObservable();  
    
    private loadAllCourses() {
    
          const loadCourses$ =  this.http.get<Course[]>('/api/courses')
            .pipe(
              map(response => response["payload"])
            );
    
          this.loading.showLoaderUntilCompleted(loadCourses$)
            .subscribe(
              courses => this.subject.next(courses)
            );
      }
  • 相关阅读:
    《花好月圆夜》
    关于Url重写
    三大WEB服务器对比分析(apache ,lighttpd,nginx)
    APC 和 Memcache 有什么区别,哪个更好效率更高?
    URL优化不仅仅是静态化重写URL
    php中的静态变量和动态变量的区别框架加载变量时运用
    msicuu.exe (msizap.exe),程序的作用
    显示器接口针脚定义(Dsub15)
    图文教程:DIY全屏开机LOGO详解
    ASP.NET中的媒体播放
  • 原文地址:https://www.cnblogs.com/Answer1215/p/12431901.html
Copyright © 2011-2022 走看看