Repository navigation
Add logic to handle any type (3.1) with additional properties - #24559
Conversation
There was a problem hiding this comment.
1 issue found across 2 files
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="modules/openapi-generator/src/main/java/org/openapitools/codegen/DefaultCodegen.java">
<violation number="1" location="modules/openapi-generator/src/main/java/org/openapitools/codegen/DefaultCodegen.java:3162">
P2: 3.1 any-type models with no explicit `nullable` flag are still marked non-nullable here, even though an empty JSON Schema accepts `null` and `updatePropertyForAnyType` marks the corresponding property nullable. Including the any-type condition would keep model metadata consistent and prevent generators that use `CodegenModel.isNullable` from producing non-nullable wrappers or serialization behavior.</violation>
</file>
Reply with feedback, questions, or to request a fix.
Re-trigger cubic
| m.dataType = getSchemaType(schema); | ||
| } | ||
| if (!ModelUtils.isAnyType(schema) && Boolean.TRUE.equals(schema.getNullable())) { | ||
| if (ModelUtils.isNullable(schema)) { |
There was a problem hiding this comment.
P2: 3.1 any-type models with no explicit nullable flag are still marked non-nullable here, even though an empty JSON Schema accepts null and updatePropertyForAnyType marks the corresponding property nullable. Including the any-type condition would keep model metadata consistent and prevent generators that use CodegenModel.isNullable from producing non-nullable wrappers or serialization behavior.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At modules/openapi-generator/src/main/java/org/openapitools/codegen/DefaultCodegen.java, line 3162:
<comment>3.1 any-type models with no explicit `nullable` flag are still marked non-nullable here, even though an empty JSON Schema accepts `null` and `updatePropertyForAnyType` marks the corresponding property nullable. Including the any-type condition would keep model metadata consistent and prevent generators that use `CodegenModel.isNullable` from producing non-nullable wrappers or serialization behavior.</comment>
<file context>
@@ -3165,7 +3159,7 @@ public CodegenModel fromModel(String name, Schema schema) {
m.dataType = getSchemaType(schema);
}
- if (!ModelUtils.isAnyType(schema) && Boolean.TRUE.equals(schema.getNullable())) {
+ if (ModelUtils.isNullable(schema)) {
m.isNullable = Boolean.TRUE;
}
</file context>
| if (ModelUtils.isNullable(schema)) { | |
| if (ModelUtils.isNullable(schema) || ModelUtils.isAnyType(schema)) { |
There was a problem hiding this comment.
1 issue found across 2 files
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="modules/openapi-generator/src/main/java/org/openapitools/codegen/DefaultCodegen.java">
<violation number="1" location="modules/openapi-generator/src/main/java/org/openapitools/codegen/DefaultCodegen.java:3163">
P1: The new condition `ModelUtils.isNullable(schema) || ModelUtils.isAnyType(schema)` marks `m.isNullable = TRUE` for every schema where `isAnyType` is true, and `isAnyType` returns true for any schema without an explicit `type` keyword — including all `allOf`/`oneOf`/`anyOf` composed models that carry only the composed keyword. Since `fromModel` runs this line before the composed-schema dispatch and `updateModelForComposedSchema` only ever sets nullable to true (never resets it), all inheritance/union models now become nullable even when the spec does not define them as nullable. This is much broader than the intended '3.1 any type is nullable' behavior and will alter generated output for many existing models; it also silently overrides an explicit `nullable: false`. Consider limiting the anyType nullable assignment to non-composed any-type schemas (and handling composed nullability through the existing composed-schema path) rather than applying it via the broad `isAnyType` check in `fromModel`.</violation>
</file>
Reply with feedback, questions, or to request a fix.
Re-trigger cubic
| } | ||
| if (!ModelUtils.isAnyType(schema) && Boolean.TRUE.equals(schema.getNullable())) { | ||
| // nullable or any type (which is nullable by default in 3.1 spec) | ||
| if (ModelUtils.isNullable(schema) || ModelUtils.isAnyType(schema)) { |
There was a problem hiding this comment.
P1: The new condition ModelUtils.isNullable(schema) || ModelUtils.isAnyType(schema) marks m.isNullable = TRUE for every schema where isAnyType is true, and isAnyType returns true for any schema without an explicit type keyword — including all allOf/oneOf/anyOf composed models that carry only the composed keyword. Since fromModel runs this line before the composed-schema dispatch and updateModelForComposedSchema only ever sets nullable to true (never resets it), all inheritance/union models now become nullable even when the spec does not define them as nullable. This is much broader than the intended '3.1 any type is nullable' behavior and will alter generated output for many existing models; it also silently overrides an explicit nullable: false. Consider limiting the anyType nullable assignment to non-composed any-type schemas (and handling composed nullability through the existing composed-schema path) rather than applying it via the broad isAnyType check in fromModel.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At modules/openapi-generator/src/main/java/org/openapitools/codegen/DefaultCodegen.java, line 3163:
<comment>The new condition `ModelUtils.isNullable(schema) || ModelUtils.isAnyType(schema)` marks `m.isNullable = TRUE` for every schema where `isAnyType` is true, and `isAnyType` returns true for any schema without an explicit `type` keyword — including all `allOf`/`oneOf`/`anyOf` composed models that carry only the composed keyword. Since `fromModel` runs this line before the composed-schema dispatch and `updateModelForComposedSchema` only ever sets nullable to true (never resets it), all inheritance/union models now become nullable even when the spec does not define them as nullable. This is much broader than the intended '3.1 any type is nullable' behavior and will alter generated output for many existing models; it also silently overrides an explicit `nullable: false`. Consider limiting the anyType nullable assignment to non-composed any-type schemas (and handling composed nullability through the existing composed-schema path) rather than applying it via the broad `isAnyType` check in `fromModel`.</comment>
<file context>
@@ -3165,7 +3159,8 @@ public CodegenModel fromModel(String name, Schema schema) {
}
- if (!ModelUtils.isAnyType(schema) && Boolean.TRUE.equals(schema.getNullable())) {
+ // nullable or any type (which is nullable by default in 3.1 spec)
+ if (ModelUtils.isNullable(schema) || ModelUtils.isAnyType(schema)) {
m.isNullable = Boolean.TRUE;
}
</file context>
There was a problem hiding this comment.
1 issue found across 2 files
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java">
<violation number="1" location="modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java:2193">
P2: Any-type schemas that only declare `additionalProperties` still bypass this new preservation logic: `normalizeSchema` classifies them as null schemas and returns the original before `processNormalize31Spec` runs. This leaves the reported OAS 3.1 case unhandled unless the schema also has a description or another field that prevents the early return; the null-schema guard should exclude schemas with `additionalProperties` or the handling should occur before that return.</violation>
</file>
Reply with feedback, questions, or to request a fix.
Re-trigger cubic
| Schema sc = new Schema<>(); | ||
|
|
||
| // additional properties set? | ||
| if (schema.getAdditionalProperties() != null) { |
There was a problem hiding this comment.
P2: Any-type schemas that only declare additionalProperties still bypass this new preservation logic: normalizeSchema classifies them as null schemas and returns the original before processNormalize31Spec runs. This leaves the reported OAS 3.1 case unhandled unless the schema also has a description or another field that prevents the early return; the null-schema guard should exclude schemas with additionalProperties or the handling should occur before that return.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java, line 2193:
<comment>Any-type schemas that only declare `additionalProperties` still bypass this new preservation logic: `normalizeSchema` classifies them as null schemas and returns the original before `processNormalize31Spec` runs. This leaves the reported OAS 3.1 case unhandled unless the schema also has a description or another field that prevents the early return; the null-schema guard should exclude schemas with `additionalProperties` or the handling should occur before that return.</comment>
<file context>
@@ -2182,13 +2182,19 @@ protected Schema processNormalize31Spec(Schema schema, Set<Schema> visitedSchema
+ Schema sc = new Schema<>();
+
+ // additional properties set?
+ if (schema.getAdditionalProperties() != null) {
+ sc.setAdditionalProperties(schema.getAdditionalProperties());
+ }
</file context>
There was a problem hiding this comment.
2 issues found across 3 files
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="modules/openapi-generator/src/main/java/org/openapitools/codegen/utils/ModelUtils.java">
<violation number="1" location="modules/openapi-generator/src/main/java/org/openapitools/codegen/utils/ModelUtils.java:2624">
P1: Schemas using the `Schema.booleanSchemaValue(false)` representation of `additionalProperties: false` can now be rewritten as maps with nullable any values: this check lets the normalizer process the parent, then misclassifies the boolean-false child as a null schema. Preserving the false form, or excluding boolean-schema values from the null-value conversion, keeps additional properties disallowed.</violation>
</file>
<file name="modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java">
<violation number="1" location="modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java:2193">
P3: When the normalizer converts a type-less 3.1 schema that has `additionalProperties` (e.g. a free-form map with a `description`, `title`, `default` or `example`), it returns a brand-new empty `Schema` and copies only `additionalProperties`, silently dropping all other sibling metadata such as description, title, default, example, and extensions. For a map schema like `{ description: 'a map', additionalProperties: { type: string } }` this means the description no longer reaches generated code. Since this branch is being extended specifically to preserve `additionalProperties`, it would be more consistent to carry over the remaining metadata too (for example, reusing an existing metadata-copy helper).</violation>
</file>
Reply with feedback, questions, or to request a fix.
Re-trigger cubic
| // schema with properties | ||
| if (schema.getProperties() != null) { | ||
| // schema with properties or additional properties | ||
| if (schema.getProperties() != null || schema.getAdditionalProperties() != null) { |
There was a problem hiding this comment.
P1: Schemas using the Schema.booleanSchemaValue(false) representation of additionalProperties: false can now be rewritten as maps with nullable any values: this check lets the normalizer process the parent, then misclassifies the boolean-false child as a null schema. Preserving the false form, or excluding boolean-schema values from the null-value conversion, keeps additional properties disallowed.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At modules/openapi-generator/src/main/java/org/openapitools/codegen/utils/ModelUtils.java, line 2624:
<comment>Schemas using the `Schema.booleanSchemaValue(false)` representation of `additionalProperties: false` can now be rewritten as maps with nullable any values: this check lets the normalizer process the parent, then misclassifies the boolean-false child as a null schema. Preserving the false form, or excluding boolean-schema values from the null-value conversion, keeps additional properties disallowed.</comment>
<file context>
@@ -2620,8 +2620,8 @@ public static boolean isNullTypeSchema(OpenAPI openAPI, Schema schema) {
- // schema with properties
- if (schema.getProperties() != null) {
+ // schema with properties or additional properties
+ if (schema.getProperties() != null || schema.getAdditionalProperties() != null) {
return false;
}
</file context>
| Schema sc = new Schema<>(); | ||
|
|
||
| // additional properties set? | ||
| if (schema.getAdditionalProperties() != null) { |
There was a problem hiding this comment.
P3: When the normalizer converts a type-less 3.1 schema that has additionalProperties (e.g. a free-form map with a description, title, default or example), it returns a brand-new empty Schema and copies only additionalProperties, silently dropping all other sibling metadata such as description, title, default, example, and extensions. For a map schema like { description: 'a map', additionalProperties: { type: string } } this means the description no longer reaches generated code. Since this branch is being extended specifically to preserve additionalProperties, it would be more consistent to carry over the remaining metadata too (for example, reusing an existing metadata-copy helper).
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java, line 2193:
<comment>When the normalizer converts a type-less 3.1 schema that has `additionalProperties` (e.g. a free-form map with a `description`, `title`, `default` or `example`), it returns a brand-new empty `Schema` and copies only `additionalProperties`, silently dropping all other sibling metadata such as description, title, default, example, and extensions. For a map schema like `{ description: 'a map', additionalProperties: { type: string } }` this means the description no longer reaches generated code. Since this branch is being extended specifically to preserve `additionalProperties`, it would be more consistent to carry over the remaining metadata too (for example, reusing an existing metadata-copy helper).</comment>
<file context>
@@ -2182,13 +2182,19 @@ protected Schema processNormalize31Spec(Schema schema, Set<Schema> visitedSchema
+ Schema sc = new Schema<>();
+
+ // additional properties set?
+ if (schema.getAdditionalProperties() != null) {
+ sc.setAdditionalProperties(schema.getAdditionalProperties());
+ }
</file context>
There was a problem hiding this comment.
1 issue found across 3 files
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java">
<violation number="1" location="modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java:2193">
P2: Schemas using `examples` are normalized with those values in the singular `example` field, so generated examples and downstream consumers can interpret the metadata incorrectly. The copy should preserve `examples` via `setExamples` (and leave `example` sourced only from `getExample`).</violation>
</file>
Reply with feedback, questions, or to request a fix.
Re-trigger cubic
| Schema sc = new Schema<>(); | ||
|
|
||
| // copy description, title, etc | ||
| ModelUtils.copyMetadata(schema, sc); |
There was a problem hiding this comment.
P2: Schemas using examples are normalized with those values in the singular example field, so generated examples and downstream consumers can interpret the metadata incorrectly. The copy should preserve examples via setExamples (and leave example sourced only from getExample).
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java, line 2193:
<comment>Schemas using `examples` are normalized with those values in the singular `example` field, so generated examples and downstream consumers can interpret the metadata incorrectly. The copy should preserve `examples` via `setExamples` (and leave `example` sourced only from `getExample`).</comment>
<file context>
@@ -2182,13 +2182,22 @@ protected Schema processNormalize31Spec(Schema schema, Set<Schema> visitedSchema
+ Schema sc = new Schema<>();
+
+ // copy description, title, etc
+ ModelUtils.copyMetadata(schema, sc);
+
+ // additional properties set?
</file context>
a follow up PR to #24558
PR checklist
Commit all changed files.
This is important, as CI jobs will verify all generator outputs of your HEAD commit as it would merge with master.
These must match the expectations made by your contribution.
You may regenerate an individual generator by passing the relevant config(s) as an argument to the script, for example
./bin/generate-samples.sh bin/configs/java*.IMPORTANT: Do NOT purge/delete any folders/files (e.g. tests) when regenerating the samples as manually written tests may be removed.
Summary by cubic
Handle OpenAPI 3.1 “any type” schemas by converting them to empty schemas while preserving
additionalPropertiesand metadata (title/description/examples), removing misleadingnullable: falselogs, and tightening null-type detection.additionalPropertiesand copy metadata when normalizing 3.1 “any type” (notype/types) to an empty schema inOpenAPINormalizer.nullable: falseon “any type” inDefaultCodegenfor models and properties.ModelUtils.isNullTypeSchema, treat schemas withpropertiesoradditionalProperties: trueas not null-type.ModelUtils.copyMetadatato copyexamplesviasetExamples(...).Written for commit f832ba7. Summary will update on new commits.