引用组件属性的OpenAPI路径参数

时间:2019-01-28 19:06:58

标签: openapi

假设我在OpenAPI文档中有一些简单的Order> OrderLines> Product Data Model。 组件部分如下所示:

components:
  schemas:
    Order:
      required:
        - orderId
      properties:
        orderId:
          type: integer
        orderlines:
          type: array
          items:
            $ref: '#/components/schemas/OrderLine'
    OrderLine:
      required:
        - orderLineId
        - product
        - price
      properties:
        orderLineId:
          type: integer
        product:
          $ref: '#/components/schemas/Product'
        price:
          type: integer
    Product:
      required:
        - productId
        - name
      x-keys:
        - productId
      properties:
        productId:
          type: integer
        name:
          type: string

在构建路径以定义用于在订单上获取特定OrderLine的api时,如下所示:

paths:
    /orders/{orderId}/orderlines/{orderLineId}:
        get:
            operationId: getOrderLine
            parameters:
               - in: path
                 name: orderId
                 schema:
                    type: integer
                 required: true
               - in: path
                 name: orderLineId
                 schema:
                    type: integer
                 required: true

现在,已定义的orderId参数实际上是指订单组件的orderId属性。参数orderLineId相同,该参数引用组件OrderLine的orderLineId属性。

那么有可能在参数定义中实际引用这些属性,而不用复制属性的类型信息吗?

我的意思是有可能做这样的事情:

paths:
    /orders/{orderId}/orderlines/{orderLineId}:
        get:
            operationId: getOrderLine
            parameters:
               - in: path
                 name: orderId
                 $ref: #components/schemas/Order/properties/orderId
                 required: true
               - in: path
                 name: orderLineId
                 $ref: #components/schemas/OrderLine/properties/orderLineId
                 required: true

1 个答案:

答案 0 :(得分:2)

首先,始终将type: object添加到您的对象定义中;仅properties关键字还不足以指示对象类型。 type不能从其他关键字和no type actually means "any type"推论得出。


关于您的问题-当然,可以$ref进行单个属性定义。您的示例几乎是正确的,您只需要:

  1. $ref放入参数schema内。

  2. #components替换为#/components

  3. 将引用值(#/components/...)括在引号中,以防止将其解析为YAML注释。

paths:
    /orders/{orderId}/orderlines/{orderLineId}:
        get:
            operationId: getOrderLine
            parameters:
               - in: path
                 name: orderId
                 schema:
                   $ref: '#/components/schemas/Order/properties/orderId'
                 required: true
               - in: path
                 name: orderLineId
                 schema:
                   $ref: '#/components/schemas/OrderLine/properties/orderLineId'
                 required: true

但是,引用属性定义并不常见,某些工具可能在处理此类引用时遇到问题。最好为要$ref的所有定义定义单独的架构:

components:    
  schemas:
    OrderId:        # <-------
      type: integer
    OrderLineId:    # <-------
      type: integer

    Order:
      type: object
      required:
        - orderId
      properties:
        orderId:
          $ref: '#/components/schemas/OrderId'      # <-------
        ...
    OrderLine:
      type: object
      required:
        - orderLineId
        - product
        - price
      properties:
        orderLineId:
          $ref: '#/components/schemas/OrderLineId'  # <-------
        ...

paths:
    /orders/{orderId}/orderlines/{orderLineId}:
        get:
            operationId: getOrderLine
            parameters:
               - in: path
                 name: orderId
                 schema:
                   $ref: '#/components/schemas/OrderId'      # <-------
                 required: true
               - in: path
                 name: orderLineId
                 schema:
                   $ref: '#/components/schemas/OrderLineId'  # <-------
                 required: true