【问题标题】:Angular loading interceptor角加载拦截器
【发布时间】:2022-02-02 17:23:15
【问题描述】:

如何避免角加载拦截器中的多次加载 在角度每个http调用加载微调器并尝试仅实现一个加载用于初始页面加载。如何解决这个问题

【问题讨论】:

    标签: javascript angular angular-http angular-http-interceptors


    【解决方案1】:

    您正在处理现有的 Angular 应用程序。

    应用程序从许多不同的组件对 REST API 进行 HTTP 调用。

    您希望为每个 HTTP 请求显示一个自定义微调器。由于这是一个现有的应用程序,因此有很多地方调用了 REST API。而且在每个地方一个一个地更改代码不是一个可行的选择。

    所以,你想实现一个抽象的解决方案来解决这个问题。

    代码可以写得更简单,无需创建新的 observable 并将请求存储在内存中。下面的代码也使用带有管道操作符的 RxJS 6:

    import { Injectable } from '@angular/core';
    import {
      HttpRequest,
      HttpHandler,
      HttpInterceptor,
      HttpResponse
    } from '@angular/common/http';
    import { finalize } from 'rxjs/operators';
    import { LoadingService } from '@app/services/loading.service';
    import { of } from 'rxjs';
    
    @Injectable()
    export class LoadingInterceptor implements HttpInterceptor {
      private totalRequests = 0;
    
      constructor(private loadingService: LoadingService) { }
    
      intercept(request: HttpRequest<any>, next: HttpHandler) {
        this.totalRequests++;
        this.loadingService.setLoading(true);
    
        return next.handle(request).pipe(
          finalize(res => {
            this.totalRequests--;
            if (this.totalRequests === 0) {
              this.loadingService.setLoading(false);
            }
          })
        );
      }
    }
    

    将此拦截器服务添加到您的模块提供程序中:

    @NgModule({
      // ...
      providers: [
        { provide: HTTP_INTERCEPTORS, useClass: LoadingInterceptor, multi: true }
      ]
    })
    export class AppModule { }
    

    这是LoadingService 实现的示例:

    @Injectable()
    export class LoadingService {
      private isLoading$$ = new BehaviorSubject<boolean>(false);
      isLoading$ = this.isLoading$$.asObservable();
      
      setLoading(isLoading: boolean) {
        this.isLoading$$.next(isLoading);
      }
    }
    

    下面是在组件中使用 LoadingService 的方法:

    @Component({
      selector: 'app-root',
      template: `
        <ng-container *ngIf="loadingService.isLoading$ | async">
          <i class="loading"></i>
        </ng-container>
        <router-outlet></router-outlet>
      `,
      changeDetection: ChangeDetectionStrategy.OnPush
    })
    export class AppComponent {
      constructor(public loadingService: LoadingService) {}
    }
    

    【讨论】:

      猜你喜欢
      • 2018-01-20
      • 1970-01-01
      • 1970-01-01
      • 2019-04-12
      • 1970-01-01
      • 2017-10-09
      • 2014-10-25
      • 1970-01-01
      • 2016-02-02
      相关资源
      最近更新 更多