将队列添加到Angular的HttpClient [英] Add queueing to Angular's HttpClient

查看:99
本文介绍了将队列添加到Angular的HttpClient的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我的要求与向Angles $ http服务添加排队完全相同a>,但需要使用@angular/common/http中的HttpInterceptor在Angular 4.3或5中实现.

I have exact same requirement as mentioned in Add queueing to angulars $http service but need implementation in Angular 4.3 or 5 using the HttpInterceptor from @angular/common/http.

我有一个非常古怪的API,该API一次只能处理特定浏览器会话的单个请求.因此,我需要确保每次在同一会话中发出请求时,该请求都会进入一个队列,并且该队列一次执行一个请求,直到它为空.

I have a very quirky API that can only handle a single request at a time for a particular browser session. Therefore, I need to ensure that every time a request is made in same session, it goes into a queue, and that queue is executed one request at a time, until it is empty.

推荐答案


解决方案


@Zlatko建议使用正确的方法,尽管其中几乎没有逻辑和语法问题,但我已将其粘贴到工作代码下面进行了纠正:


Solution


@Zlatko has suggested correct approach, although there are few logical and syntax issues in it but I have corrected it pasting below a working code:

import { Injectable } from '@angular/core';
import { Response } from '@angular/http';
import { HttpClient } from '@angular/common/http';
import { Observable } from 'rxjs/Observable';
import { Subject } from 'rxjs/Subject'

export class PendingRequest {
  url: string;
  method: string;
  options: any;
  subscription: Subject<any>;

  constructor(url: string, method: string, options: any, subscription: Subject<any>) {
    this.url = url;
    this.method = method;
    this.options = options;
    this.subscription = subscription;
  }
}

@Injectable()
export class BackendService {
  private requests$ = new Subject<any>();
  private queue: PendingRequest[] = [];

  constructor(private httpClient: HttpClient) {
    this.requests$.subscribe(request => this.execute(request));
  }

  /** Call this method to add your http request to queue */
  invoke(url, method, params, options) {
    return this.addRequestToQueue(url, method, params, options);
  }

  private execute(requestData) {
    //One can enhance below method to fire post/put as well. (somehow .finally is not working for me)
    const req = this.httpClient.get(requestData.url)
      .subscribe(res => {
        const sub = requestData.subscription;
        sub.next(res);
        this.queue.shift();
        this.startNextRequest();
      });
  }

  private addRequestToQueue(url, method, params, options) {
    const sub = new Subject<any>();
    const request = new PendingRequest(url, method, options, sub);

    this.queue.push(request);
    if (this.queue.length === 1) {
      this.startNextRequest();
    }
    return sub;
  }

  private startNextRequest() {
    // get next request, if any.
    if (this.queue.length > 0) {
      this.execute(this.queue[0]);
    }
  }
}

一个人可以通过以下方式使用/调用上述服务(从任何其他组件或服务)进行HTTP调用(很明显,您需要在组件中注入BackendService,例如在组件提供者中提及并在构造函数中进行定义):

One can use/call above service following way to make HTTP calls (from any other component or service) (Obviously you need to inject BackendService in the component e.g. Mention in provider of component and define in constructor):

    this.backendService.invoke('https://jsonplaceholder.typicode.com/posts', 'Get', null, null)
    .subscribe(
      result => {
        this.data = result;
      }
    );

如果有人想看一下工作的插棒,那么这是工作的插棒

In case of someone wants to look at working plunker then here is the working plunker.

这篇关于将队列添加到Angular的HttpClient的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆