繁体   English   中英

NestJS HttpService All Method API 使用Interceptor时调用不起作用

[英]NestJS HttpService All Method API Call is not working when Interceptor is used

NestJS API App 使用 HttpService 调用另一个 API 并且它在没有使用自定义拦截器时工作。 HttpService API 调用已执行,但未到达另一个 API 并且看不到响应。

这是获取呼叫代码


 get(path: string, body: any = {}): Observable<AxiosResponse<any>> {
    console.log('DomainAPI Response Begining');
    const url = this.baseURL + path;
    this.updateLastUtilizedTimestamp();
    return this.httpService.get(url, { validateStatus: null }).pipe(
      tap(data => {
        console.log('DomainAPI Response Tap', data);
      }),
      retryWhen(
        this.rxJSUtilsService.genericRetryStrategy({
          numberOfAttempts: 3,
          delayTime: 200,
          ignoredErrorCodes: [500],
        }),
      ),
      catchError(this.formatErrors),
    );
  }

如果使用任何自定义拦截器,我在调试时发现以下内容。

arguments:TypeError: 'caller', 'callee', and 'arguments' properties may not be accessed on strict mode functions or the arguments objects for calls to them

Postman 显示以下响应。

{
    "statusCode": 500,
    "message": {
        "Title": "TypeError",
        "Type": "Error",
        "Detail": "Converting circular structure to JSON\n    --> starting at object with constructor 'Observable'\n    |     property 'operator' -> object with constructor 'CatchOperator'\n    --- property 'caught' closes the circle",
        "Status": "Status",
        "Extension": ""
    },
    "timestamp": "Exception - AllExceptionsFilter 2019-12-26T17:29:42.447Z"
}

我将上面的内容更改如下,但仍然无法正常工作


get(path: string, body: any = {}) {
    console.log('DomainAPI Response Begining');
    const url = this.baseURL + path;
    this.updateLastUtilizedTimestamp();
    return this.httpService.get(url, { validateStatus: null }).pipe(
      map(response => {
        console.log('DomainAPI Response Tap', response.data);
        return response.data;
      }),
    );
  }

它在 postman 中给出以下响应


{
    "data": {
        "_isScalar": false,
        "source": {
            "_isScalar": false,
            "source": {
                "_isScalar": false
            },
            "operator": {}
        },
        "operator": {}
    }
}

请指教

async get(path: string, body: any = {}): Promise<any> {
    ...
    const res = await this.httpService.get(url, { validateStatus: null }).toPromise();

    return res.data;
  }
get(path: string, body: any = {}) {
   ...
    return this.httpService.get(url, { validateStatus: null })
    .toPromise()
    .then(res => res.data)
    .catch(err => this.logger.error(err));
  }

使用 .toPromise() 方法转换为 promise 已被弃用,因为我们正在使用可观察对象,并且 promise 仅返回一个值,而可观察对象可能不返回任何值或返回多个值(参见更多@:转换为承诺)。 因此,作为使用上述问题的示例,解决方案将是:

import { lastValueFrom } from 'rxjs';

get(path: string, body: any = {}): Observable<AxiosResponse<any>> {
    console.log('DomainAPI Response Begining');
    const url = this.baseURL + path;
    this.updateLastUtilizedTimestamp();
 
    return await lastValueFrom(
      this.httpService.get(url, { validateStatus: null })
      .pipe(
      tap(data => {
        console.log('DomainAPI Response Tap', data);
      }),
      retryWhen(
        this.rxJSUtilsService.genericRetryStrategy({
          numberOfAttempts: 3,
          delayTime: 200,
          ignoredErrorCodes: [500],
        }),
      ),
      catchError(this.formatErrors),
    ));
  }

基本上你所要做的就是用 firstValueFrom 或 lastValueFrom 包装整个 http 请求,在这种情况下 lastValueFrom 是合适的。 请访问 rxjs 上面关于转换为承诺的文档的链接,以了解更多信息。

注意:我只添加了 lastValueFrom 导入,只是作为所需内容的明确指示。

这是使用我自己的代码的另一个示例:

async send_otp(
    phone: string,
    channel: string,
    ): Promise<Observable<AxiosResponse<any>>> {
    return await lastValueFrom(
      this.httpService
        .post(`/messaging/otp/`, {
          sender: 'Oyinkayy',
          destination: '234' + String(phone).slice(1),
          length: 6,
          channel: channel,
          reference: '',
        })
        .pipe(
          tap((resp) => console.log(resp)),
          map((resp) => {
            return resp.data;
          }),
          tap((data) => console.log(data)),
          catchError(async (err) => {
            return err;
          }),
        ),
    );
   }

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM