Skip to content

Breaking changes are missed when a schema $ref is replaced or retargeted #663

Open

Description

@josephaxisa

When a schema $ref is replaced by an inline schema, an inline schema by a $ref, or a $ref is pointed at another schema, CompareSchemas records a non-breaking $ref change and returns. The new schema is never compared, so breaking changes in it are missed.

# old.yaml
openapi: 3.1.1
info: {title: Pets, version: '1'}
paths:
  /pets:
    post:
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/Pet'
      responses:
        '200': {description: The pet}
components:
  schemas:
    Pet:
      type: object
      properties:
        name: {type: string}

new.yaml is the same, except the request body schema is inlined and requires name:

            schema:
              type: object
              properties:
                name: {type: string}
              required: [name]

openapi-changes report old.yaml new.yaml (0.2.13) reports 1 change, 0 breaking. The same required change between two inline schemas is reported as breaking. TestCompareSchemas_PropertyRefChange_Fail shows the same thing: a $ref to a type: int schema becomes inline type: string, and only the non-breaking $ref change is reported.

Removing the early return sc isn't enough: it was added to stop over-cycling (TestCheckExplodedFileCheck asserts the single $ref change), and falling through re-compares shared subtrees once per path, which grows exponentially when a tree of schemas is renamed. It also bypasses the object→composition handling from #650, so $ref: Pet → anyOf: [$ref Pet, null] reports false breaking changes. A fix probably needs to remember which schema pairs were already compared. How would you like this approached? Happy to help with a PR.

Related: #662

Activity

  1. josephaxisa commented on Oct 22, 2026

    @josephaxisa
    ContributorAuthor

    @daveshanley opened #668 for this. It keeps the $ref change and compares the resolved schemas (with guards for circular refs, unresolved targets, and 3.1 $ref siblings, plus looking through $ref in #650's composition helpers)

  2. daveshanley commented on Oct 24, 2026

    @daveshanley
    Member

    Thanks for the clear repro. Review is up on #668: right direction, one blocker (exponential blow-up on shared schema graphs) with a suggested fix. Once that is sorted, this lands.

  3. added a commit that references this issue on Oct 25, 2026
    ffb70f0
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions