cebe / php-openapi

Read and write OpenAPI yaml/json files and make the content accessible in PHP objects.
MIT License
469 stars 89 forks source link

Reference parsing doesn't work in the CLI tool using relative paths. #164

Open shulard opened 2 years ago

shulard commented 2 years ago

Hello !

First, thank you for your awesome library, it helps us a lot manipulating our OpenAPI definitions.

We found a tiny issue about reference resolution in our local configuration.

I give you a tiny sample to describe our usage. We have a doc/api folder which contains an openapi.yaml file like this :

openapi: 3.0.3
paths:
  /api/files:
    $ref: upload/files.yaml

Then here is the doc/api/upload/files.yaml :

get:
  operationId: getUploadFiles
  summary: Get all the non deleted uploaded file batchs
  responses:
    '200':
      content:
        'application/json':
          schema:
            $ref: './../schema/file.yaml#/FileListResponse'

And finally the doc/api/schema/file.yaml which looks like :

File:
  type: object
  required:
    - id
    - type
    - attributes
  properties:
    type:
      type: string
      example: file
    id:
      type: string
      format: UUIDv4
      example: d6e6ad56-3874-48c7-9265-97f27808dac3
    attributes:
      type: object
    relationships:
      type: object

ArrayOfFile:
  type: array
  items:
    $ref: '#/File'

FileListResponse:
  type: object
  properties:
    data:
      $ref: '#/ArrayOfFile'

As you can see, we use relative paths in our $ref attributes. I simplified a bit the definition but the idea is here. Whenever a $ref contains .., there are skipped.

I checked in the library code and found that the cebe\openapi\ReferenceContext::reduceDots remove all the .. from the given paths. If I just skip this methods, my API doc is correctly imported and used.

I don't know what's the expected behavior here. If I can help (giving more details or contributing code), I'll be glad to do it ^^

cebe commented 2 years ago

thanks for reporting this. reduceDots does not simply remove the dots, it should resolve cases like e.g. /some/path/to/subdir/../../openapi.yml to /some/path/openapi.yml. There might be a bug so that it does not do that correctly in your case.

cebe commented 2 years ago

added a failing test for this case. You can work around it by removing the reference to the current directory: ./ this should work:

        $ref: '../schema/file.yaml#/FileListResponse'
shulard commented 2 years ago

Ok, thank you for the ./ fix, it works on my side ^^