daveshanley / vacuum

vacuum is the worlds fastest OpenAPI 3, OpenAPI 2 / Swagger linter and quality analysis tool. Built in go, it tears through API specs faster than you can think. vacuum is compatible with Spectral rulesets and generates compatible reports.
https://quobix.com/vacuum
MIT License
580 stars 48 forks source link

Infinite loop with `$` in component #393

Closed gnuletik closed 9 months ago

gnuletik commented 9 months ago

When using an invalid $ref value by using a $ character instead of #, vacuum goes into an infinite loop with the process using 100% of CPU.

sample:

          content:
            application/json:
              schema:
                $ref: "$/components/schemas/Pets"

$ vacuum lint --details petstore.yaml

██╗   ██╗ █████╗  ██████╗██╗   ██╗██╗   ██╗███╗   ███╗
██║   ██║██╔══██╗██╔════╝██║   ██║██║   ██║████╗ ████║
██║   ██║███████║██║     ██║   ██║██║   ██║██╔████╔██║
╚██╗ ██╔╝██╔══██║██║     ██║   ██║██║   ██║██║╚██╔╝██║
 ╚████╔╝ ██║  ██║╚██████╗╚██████╔╝╚██████╔╝██║ ╚═╝ ██║
  ╚═══╝  ╚═╝  ╚═╝ ╚═════╝ ╚═════╝  ╚═════╝ ╚═╝     ╚═╝

version: 0.5.10 | compiled: Thu, 07 Dec 2023 09:17:12 UTC
🔗 https://quobix.com/vacuum | https://github.com/daveshanley/vacuum

 INFO  Linting file 'petstore.yaml' against 42 rules: https://quobix.com/vacuum/rulesets/recommended
Petstore.yaml (error on line 36) ```yaml openapi: "3.0.0" info: version: 1.0.0 title: Swagger Petstore license: name: MIT servers: - url: http://petstore.swagger.io/v1 paths: /pets: get: summary: List all pets operationId: listPets tags: - pets parameters: - name: limit in: query description: How many items to return at one time (max 100) required: false schema: type: integer maximum: 100 format: int32 responses: '200': description: A paged array of pets headers: x-next: description: A link to the next page of responses schema: type: string content: application/json: schema: $ref: "$/components/schemas/Pets" default: description: unexpected error content: application/json: schema: $ref: "#/components/schemas/Error" post: summary: Create a pet operationId: createPets tags: - pets responses: '201': description: Null response default: description: unexpected error content: application/json: schema: $ref: "#/components/schemas/Error" /pets/{petId}: get: summary: Info for a specific pet operationId: showPetById tags: - pets parameters: - name: petId in: path required: true description: The id of the pet to retrieve schema: type: string responses: '200': description: Expected response to a valid request content: application/json: schema: $ref: "#/components/schemas/Pet" default: description: unexpected error content: application/json: schema: $ref: "#/components/schemas/Error" components: schemas: Pet: type: object required: - id - name properties: id: type: integer format: int64 name: type: string tag: type: string Pets: type: array maxItems: 100 items: $ref: "#/components/schemas/Pet" Error: type: object required: - code - message properties: code: type: integer format: int32 message: type: string ```
daveshanley commented 9 months ago

Now this is a find! I've seen this exact bug out in the wild, but I was never quite sure what was triggering it.

daveshanley commented 9 months ago

Can you try v0.5.11

gnuletik commented 9 months ago

Works like a charm! Thanks for your fast response & fix, once again!

daveshanley commented 9 months ago

This bug has been causing me more grief than I would care to admit. Thank you for finding a way to trigger it, I knew it was there, I could just not get it to fire.