Angular: 如何在 HTTP 响应缓慢时显示内容

Angular: How to show something on slow HTTP response

在我的 angular 应用程序中,我想显示具有 取消重新加载 的 text/modal按钮,当服务器响应缓慢时。

如果用户点击取消,当前的http请求将被取消。如果用户单击重新加载,将重试当前的 http 请求。如果 text/modal 已经显示并且 HTTP 请求已经 respond/completed,那么 text/modal 应该消失。

我有一个使用 HTTP 拦截器、RxJS 和全局服务的想法,但实现起来并不容易。

有没有人知道如何以正确的方式做到这一点?

编辑:哦,我想让它成为一个通用模块,这样每个 http 请求都可以取消或重新加载。所以每个页面都可以有这个功能

假设您的请求需要 20 秒才能完成响应,那么您可以在 20 秒内取消它

只需UnSubscription那个请求

import { Component, OnInit, OnDestroy } from '@angular/core';
    import { Subscription } from 'rxjs/Rx';

    export class Component implements OnInit, OnDestroy {
        private subscription: Subscription;
        ngOnInit() {
            this.subscription = this.route.params.subscribe();
        }
        ngOnDestroy() {
            this.subscription.unsubscribe();
        }



     cancel() {
            this.subscription.unsubscribe();
        }

    retry() {
            this.subscription.subscribe();
        }



    }

html 当您发出任何 http 请求时,您可以在任何时间或任何地方弹出哪个按钮,以便能够取消它

     <div> {{ subscription | async }}</div>
.
.
.Enter your other logic
.


    <button (click)=="cancel()" > Cancel Request</button>
    <button (click)=="retry()" > Cancel retry</button>

您需要使用 reportProgress of HttpRequest. There is an explanation how to do it here 。但请记住,它会监听每次更改检测,从而大大降低应用程序性能。它推荐用于大量请求(即文件上传)

Cancel/abort 所有带有 takeUntil

的未决 HTTP 请求

您可以使用 takeUntil 来停止正在进行的请求,因为来自 HttpClient returns 的请求可以很容易地做到:

TS

userStop$: Subject<boolean> = new Subject<boolean>();

makeRequest() {
    this.userStop$.next(false);
    // Service Call
    this.apiService.makeRequest().pipe(
        takeUntil(this.userStop$)
    ).subscribe(...);
}

handleUserStop() {
    this.userStop$.next(true);
}

例如,当您通过单击按钮将 userStop$ 更改为 true 时,它​​将停止。要重试,您只需调用服务方法并将 userStop$ 设置为 false;

如果请求失败后想重试,可以使用retry(x).

this.apiService.makeRequest().pipe(
    //retry 2 times on error
    retry(2)
).subscribe(...);

你也可以看看这个:

更多信息:https://www.learnrxjs.io/operators/filtering/takeuntil.html

  1. 创建可取消订阅

那个很简单。在组件中创建一个 属性 像这样:

dataSubscription: Subscription

并在您触发请求的事件处理程序中,像这样创建它:

dataSubscription = someService.someRESTApiCalls.subscribe(....)

任何时候,你想停止这个,你可以打电话给

this.dataSubscription.unsubscribe()

我还建议使用 ngOnDestroy 挂钩,并在需要时取消订阅:

ngOnDestroy(){

   if(this.dataSubscription) this.dataSubscription.unsubscribe();
}

取消通话。

  1. 模态

对于模态框,我推荐Angular Material Modal

  1. 逻辑

在组件isResponseArrived: boolean中创建一个class属性什么的。用户发起请求后,在事件处理程序中将其设置为false,并显示任何你想显示的内容,带有ngIf="!isResponseArrived"˛响应到达后,在订阅响应处理程序中将标志值修改为true(两者有值,或出错)。

+1: 检测订阅时间是否过长

使用 httpClient 超时():

this.httpClient.get(url, { headers: headers })
        .timeout(30000)
        .subscribe(
            (response) => {
                ...
            },
            error => {
                ...
            }
                ...
            );