-
Notifications
You must be signed in to change notification settings - Fork 9.2k
Description
Description
After upgrading an API specification from OpenAPI 3.0.3 to 3.1.0, I observed a change in how schemas are identified and named.
When a response schema is defined externally and referenced via $ref, operation-based response model names name are generated instead of using the original schema, even when the referenced schema is explicitly named.
This results in verbose and unstable class/model names that depend on the endpoint and HTTP status code rather than the schema definition itself.
Observed Behavior
Example:
For example I have a 'schemas' directory and inside there are .yaml files containing schemas which can be used inside my main swagger.yaml file.
api/
├── swagger.yaml
└── schemas/
└── common.yaml
swagger.yaml
openapi: 3.1.0
info:
title: Example API
version: 1.0.0
paths:
/items:
get:
summary: Retrieve a list of items
operationId: getItems
responses:
200:
description: Successful response
content:
application/json:
schema:
$ref: schemas/common.yaml#/components/schemas/ListResponse
schemas/common.yaml
components:
schemas:
ListResponse:
type: object
properties:
data:
type: array
items:
$ref: '#/components/schemas/Item'
total:
type: integer
required:
- data
- total
Item:
type: object
properties:
id:
type: string
name:
type: string
required:
- id
- name
Observed Result
When generating models from swagger.yaml, tools generate response models named similarly to:
GetItems200Response
GetItems200ResponseDataInner
Instead of using the referenced schema name:
ListResponse
Item
Expected behavior
Because ListResponse and Item are explicitly named schemas, generator should be able to reuse those names when generating models, regardless of the schemas being defined in an external file.
What I have tried
1. Defined schemas in the root components/schemas
swagger.yaml
openapi: 3.1.0
info:
title: Example API
version: 1.0.0
paths:
/items:
get:
summary: Retrieve items
operationId: getItems
responses:
200:
description: OK
content:
application/json:
schema:
$ref: '#/components/schemas/ListResponse'
components:
schemas:
ListResponse:
type: object
properties:
data:
type: array
items:
$ref: '#/components/schemas/Item'
total:
type: integer
required:
- data
- total
Item:
type: object
properties:
id:
type: string
name:
type: string
required:
- id
- name
Observed result
Tooling generates clean, reusable models:
ListResponse
Item
(or prefixed equivalents, depending on generator configuration)
2. Defined schemas in the root components/schemas but with $ref
swagger.yaml
openapi: 3.1.0
info:
title: Example API
version: 1.0.0
paths:
/items:
get:
summary: Retrieve items
operationId: getItems
responses:
200:
description: OK
content:
application/json:
schema:
$ref: '#/components/schemas/ListResponse'
components:
schemas:
ListResponse:
$ref: 'schemas/common.yaml#/ListResponse'
Observed result
Generates clean, reusable model for the ListResponse,
but the data field inside the ListResponse.java is List<GetItems200ResponseDataInner> data;
This demonstrates that schema identity is only preserved at the first level. Nested schemas referenced inside externally defined schemas still lose their original names and are treated as anonymous, resulting in operation-based generated names.
Questions / Expected Guidance
- Is this behavior an intentional design decision in OpenAPI 3.1?
- Should tools be expected to preserve the names of referenced schemas,
regardless of whether they are defined in the root document or an external file? - Is there any planned mechanism (or recommended pattern) for preserving schema
identity across files without redefining all schemas under the root
components/schemas? - If this is expected behavior, should it be explicitly documented in the
specification to avoid confusion when upgrading from OpenAPI 3.0.x?