回送4 OpenAPI连接器:指定每个请求的授权标头值

时间:2020-04-14 12:34:55

标签: loopbackjs openapi

我已经按照here中所述在Loopback 4中设置了OpenAPI连接器,并且对于未经授权的请求,它运行良好;我设法创建了各自的数据源,服务和控制器。我的服务类似于GeocoderProvider example,但可以使用以下服务界面。

export interface MyExternalService {
  search_stuff(params: {query?: string}): Promise<MyExternalServiceResponse>;
}

export interface MyExternalServiceResponse {
  text: string;
}

我从控制器中这样调用它,其中this.myExternalService是注入的服务(有点不相关,但是Loopback还可以隐式解析来自外部API数据源的JSON响应吗?):

  @get('/search')
  async searchStuff(@param.query.string('query') query: string): Promise<void> {
    return JSON.parse(
      (await this.myExternalService.search_stuff({query})).text,
    );
  }

现在,与myExternalService.search_stuff相对应的外部端点需要一个Authorization: Bearer <token>头,其中令牌是由客户端发送到回送 的,即它不是静态API密钥或所以。假设我将@param.query.string('token') token: string添加到了searchStuff控制器方法的参数列表中,如何将该令牌转发到OpenAPI连接器?这是基础OpenAPI YAML定义文件的相关部分:

paths:
  /search:
    get:
      security:
        - Authorization: []
      responses:
        '200':
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/SearchResults'
      operationId: search-stuff
components:
  securitySchemes:
    Authorization:
      type: http
      scheme: Bearer

2 个答案:

答案 0 :(得分:0)

我现在正在使用OpenAPI连接器的基础execute函数并手动拦截请求(传递给requestInterceptor的对象随后由Swagger直接传递给http模块):

    return JSON.parse(
      (
        await this.myExternalService.execute(
          'search_stuff',
          {query},
          {
            requestInterceptor: (req: {headers: {Authorization: string}}) => {
              req.headers.Authorization = 'Bearer ' + token;
              return req;
            },
          },
        )
      ).text,
    );

我还受the connector's actual execute function的启发,在MyExternalService界面中添加了以下方法:

  execute(
    operationId: string,
    parameters: object,
    options: object,
  ): Promise<MyExternalServiceResponse>;

我发现的一些东西

  • 环回内部使用swagger-client模块来执行基于OpenAPI的请求。
  • 尤其是Swagger的execute函数的securities选项期望使用Security Definitions Object。也有some quirks实际上也将其传递给Swagger。
  • 在内部,Swagger构建发出here in its source code的最终HTTP请求。此处提到了securities键,但实际上从未将其用于请求。这意味着在this.myExternalService.execute的第三个参数中手动指定它不会改变。

我还不会接受这个答案,我期待找到一种更类似于回送的方法。

答案 1 :(得分:0)

我像这样配置了我的服务,以注入基本身份验证。

import {inject, lifeCycleObserver, LifeCycleObserver} from '@loopback/core';
import {juggler} from '@loopback/repository';
const SwaggerClient = require('swagger-client');

const config = {
  name: 'jira',
  connector: 'openapi',
  spec: 'swagger-v2.json',
  validate: false,
  httpClient: (request: any) => {
    request.headers["Authorization"] = "Basic " + Buffer.from("test:test").toString('base64');
    return SwaggerClient.http(request);
  },
};

@lifeCycleObserver('datasource')
export class JiraDataSource extends juggler.DataSource
  implements LifeCycleObserver {
  static dataSourceName = 'jira';
  static readonly defaultConfig = config;

  constructor(
    @inject('datasources.config.jira', {optional: true})
    dsConfig: object = config,
  ) {
    super(dsConfig);
  }
}