Skip to content

Commit cbc64e8

Browse files
authored
Update inline model resolver to flatten responses (OpenAPITools#19992)
* update inline model resolver flatten responses * minor update * minor update * minor update * minor update
1 parent 25b6fd3 commit cbc64e8

File tree

7 files changed

+109
-20
lines changed

7 files changed

+109
-20
lines changed

modules/openapi-generator/src/main/java/org/openapitools/codegen/DefaultCodegen.java

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4774,7 +4774,7 @@ public CodegenOperation fromOperation(String path,
47744774
op.hasRequiredParams = op.requiredParams.size() > 0;
47754775

47764776
// check if the operation has only a single parameter
4777-
op.hasSingleParam = op.allParams.size() == 1;
4777+
op.hasSingleParam = op.allParams.size() == 1;
47784778

47794779
// set Restful Flag
47804780
op.isRestfulShow = op.isRestfulShow();
@@ -5724,7 +5724,7 @@ public void addOperationToGroup(String tag, String resourcePath, Operation opera
57245724
// check for operationId uniqueness
57255725
String uniqueName = co.operationId;
57265726
int counter = seenOperationIds.getOrDefault(uniqueName, 0);
5727-
while(seenOperationIds.containsKey(uniqueName)) {
5727+
while (seenOperationIds.containsKey(uniqueName)) {
57285728
uniqueName = co.operationId + "_" + counter;
57295729
counter++;
57305730
}
@@ -6120,7 +6120,7 @@ private String uniqueCaseInsensitiveString(String value, Map<String, String> see
61206120
return seenValues.get(value);
61216121
}
61226122

6123-
Optional<Entry<String,String>> foundEntry = seenValues.entrySet().stream().filter(v -> v.getValue().toLowerCase(Locale.ROOT).equals(value.toLowerCase(Locale.ROOT))).findAny();
6123+
Optional<Entry<String, String>> foundEntry = seenValues.entrySet().stream().filter(v -> v.getValue().toLowerCase(Locale.ROOT).equals(value.toLowerCase(Locale.ROOT))).findAny();
61246124
if (foundEntry.isPresent()) {
61256125
int counter = 0;
61266126
String uniqueValue = value + "_" + counter;
@@ -8181,7 +8181,7 @@ protected boolean executePostProcessor(String[] commandArr) {
81818181
int exitValue = p.exitValue();
81828182
if (exitValue != 0) {
81838183
try (InputStreamReader inputStreamReader = new InputStreamReader(p.getErrorStream(), StandardCharsets.UTF_8);
8184-
BufferedReader br = new BufferedReader(inputStreamReader)) {
8184+
BufferedReader br = new BufferedReader(inputStreamReader)) {
81858185
StringBuilder sb = new StringBuilder();
81868186
String line;
81878187
while ((line = br.readLine()) != null) {

modules/openapi-generator/src/main/java/org/openapitools/codegen/InlineModelResolver.java

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,7 @@ void flatten(OpenAPI openAPI) {
107107

108108
flattenPaths();
109109
flattenComponents();
110+
flattenComponentResponses();
110111
}
111112

112113
/**
@@ -352,7 +353,7 @@ private void gatherInlineModels(Schema schema, String modelPrefix) {
352353
}
353354

354355
if (items == null) {
355-
LOGGER.debug("prefixItems in array schema is not supported at the moment: {}", schema.toString());
356+
LOGGER.debug("prefixItems in array schema is not supported at the moment: {}", schema.toString());
356357
return;
357358
}
358359
String schemaName = resolveModelName(items.getTitle(), modelPrefix + this.inlineSchemaOptions.get("ARRAY_ITEM_SUFFIX"));
@@ -568,6 +569,20 @@ private void flattenResponses(String modelName, Operation operation) {
568569
}
569570
}
570571

572+
/**
573+
* Flatten inline models in the responses section in the components.
574+
*/
575+
private void flattenComponentResponses() {
576+
Map<String, ApiResponse> apiResponses = openAPI.getComponents().getResponses();
577+
if (apiResponses == null) {
578+
return;
579+
}
580+
581+
for (Map.Entry<String, ApiResponse> entry : apiResponses.entrySet()) {
582+
flattenContent(entry.getValue().getContent(), null);
583+
}
584+
}
585+
571586
/**
572587
* Flattens properties of inline object schemas that belong to a composed schema into a
573588
* single flat list of properties. This is useful to generate a single or multiple

modules/openapi-generator/src/main/java/org/openapitools/codegen/OpenAPINormalizer.java

Lines changed: 33 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -287,6 +287,7 @@ void normalize() {
287287
normalizeInfo();
288288
normalizePaths();
289289
normalizeComponentsSchemas();
290+
normalizeComponentsResponses();
290291
}
291292

292293
/**
@@ -445,12 +446,19 @@ private void normalizeResponses(Operation operation) {
445446
}
446447

447448
for (Map.Entry<String, ApiResponse> responsesEntry : responses.entrySet()) {
448-
if (responsesEntry.getValue() == null) {
449-
continue;
450-
} else {
451-
normalizeContent(ModelUtils.getReferencedApiResponse(openAPI, responsesEntry.getValue()).getContent());
452-
normalizeHeaders(ModelUtils.getReferencedApiResponse(openAPI, responsesEntry.getValue()).getHeaders());
453-
}
449+
normalizeResponse(responsesEntry.getValue());
450+
}
451+
}
452+
453+
/**
454+
* Normalizes schemas in ApiResponse
455+
*
456+
* @param apiResponse API response
457+
*/
458+
private void normalizeResponse(ApiResponse apiResponse) {
459+
if (apiResponse != null) {
460+
normalizeContent(ModelUtils.getReferencedApiResponse(openAPI, apiResponse).getContent());
461+
normalizeHeaders(ModelUtils.getReferencedApiResponse(openAPI, apiResponse).getHeaders());
454462
}
455463
}
456464

@@ -502,11 +510,25 @@ private void normalizeComponentsSchemas() {
502510
}
503511
}
504512

513+
/**
514+
* Normalizes schemas in component's responses.
515+
*/
516+
private void normalizeComponentsResponses() {
517+
Map<String, ApiResponse> apiResponses = openAPI.getComponents().getResponses();
518+
if (apiResponses == null) {
519+
return;
520+
}
521+
522+
for (Map.Entry<String, ApiResponse> entry : apiResponses.entrySet()) {
523+
normalizeResponse(entry.getValue());
524+
}
525+
}
526+
505527
/**
506528
* Auto fix a self referencing schema using any type to replace the self-referencing sub-item.
507529
*
508-
* @param name Schema name
509-
* @param schema Schema
530+
* @param name Schema name
531+
* @param schema Schema
510532
*/
511533
public void fixSelfReferenceSchema(String name, Schema schema) {
512534
if (ModelUtils.isArraySchema(schema)) {
@@ -993,7 +1015,6 @@ private Schema processSimplifyAnyOfStringAndEnumString(Schema schema) {
9931015
}
9941016

9951017

996-
9971018
/**
9981019
* If the schema is oneOf and the sub-schemas is null, set `nullable: true`
9991020
* instead.
@@ -1012,7 +1033,7 @@ private Schema processSimplifyOneOf(Schema schema) {
10121033
// simplify any type with 6 sub-schemas (string, integer, etc) in oneOf
10131034
if (oneOfSchemas.size() == 6) {
10141035
TreeSet<String> ts = new TreeSet<>();
1015-
for (Schema s: oneOfSchemas) {
1036+
for (Schema s : oneOfSchemas) {
10161037
s = ModelUtils.getReferencedSchema(openAPI, s);
10171038
String type = ModelUtils.getType(s);
10181039
if (type == null) {
@@ -1113,6 +1134,7 @@ private Schema setNullable(Schema schema) {
11131134
schema.setNullable(true);
11141135
return schema;
11151136
}
1137+
11161138
/**
11171139
* Set nullable to true in map if needed.
11181140
*
@@ -1148,7 +1170,7 @@ private Schema processSimplifyAnyOf(Schema schema) {
11481170
// simplify any type with 6 sub-schemas (string, integer, etc) in anyOf
11491171
if (anyOfSchemas.size() == 6) {
11501172
TreeSet<String> ts = new TreeSet<>();
1151-
for (Schema s: anyOfSchemas) {
1173+
for (Schema s : anyOfSchemas) {
11521174
s = ModelUtils.getReferencedSchema(openAPI, s);
11531175
String type = ModelUtils.getType(s);
11541176
if (type == null) {

modules/openapi-generator/src/test/java/org/openapitools/codegen/InlineModelResolverTest.java

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -352,6 +352,14 @@ public void resolveInlineArraySchemaWithTitle() {
352352
assertTrue(user.getProperties().get("city") instanceof StringSchema);
353353
}
354354

355+
@Test
356+
public void resolveComponentsResponses() {
357+
OpenAPI openAPI = TestUtils.parseSpec("src/test/resources/3_0/inline_model_resolver.yaml");
358+
new InlineModelResolver().flatten(openAPI);
359+
ApiResponse apiResponse = openAPI.getComponents().getResponses().get("JustAnotherResponse");
360+
assertEquals(apiResponse.getContent().get("application/json").getSchema().get$ref(), "#/components/schemas/inline_object");
361+
}
362+
355363
@Test
356364
public void resolveRequestBodyInvalidRef() {
357365
OpenAPI openAPI = TestUtils.parseSpec("src/test/resources/3_0/invalid_ref_request_body.yaml");
@@ -1043,7 +1051,7 @@ public void testInlineSchemaNameMapping() {
10431051
public void testInlineSchemaOptions() {
10441052
OpenAPI openAPI = TestUtils.parseSpec("src/test/resources/3_0/inline_model_resolver.yaml");
10451053
InlineModelResolver resolver = new InlineModelResolver();
1046-
Map<String, String> inlineSchemaOptions= new HashMap<>();
1054+
Map<String, String> inlineSchemaOptions = new HashMap<>();
10471055
inlineSchemaOptions.put("ARRAY_ITEM_SUFFIX", "_something");
10481056
resolver.setInlineSchemaOptions(inlineSchemaOptions);
10491057
resolver.flatten(openAPI);
@@ -1135,7 +1143,7 @@ public void testNestedAnyOf() {
11351143
public void resolveOperationInlineEnum() {
11361144
OpenAPI openAPI = TestUtils.parseSpec("src/test/resources/3_0/inline_model_resolver.yaml");
11371145
Parameter parameter = openAPI.getPaths().get("/resolve_parameter_inline_enum").getGet().getParameters().get(0);
1138-
assertNull(((ArraySchema) parameter.getSchema()).getItems().get$ref() );
1146+
assertNull(((ArraySchema) parameter.getSchema()).getItems().get$ref());
11391147

11401148
InlineModelResolver resolver = new InlineModelResolver();
11411149
Map<String, String> inlineSchemaOptions = new HashMap<>();
@@ -1145,7 +1153,7 @@ public void resolveOperationInlineEnum() {
11451153

11461154
Parameter parameter2 = openAPI.getPaths().get("/resolve_parameter_inline_enum").getGet().getParameters().get(0);
11471155
assertEquals("#/components/schemas/resolveParameterInlineEnum_status_inline_enum_parameter_inner",
1148-
((ArraySchema) parameter2.getSchema()).getItems().get$ref() );
1156+
((ArraySchema) parameter2.getSchema()).getItems().get$ref());
11491157

11501158
}
11511159

modules/openapi-generator/src/test/java/org/openapitools/codegen/OpenAPINormalizerTest.java

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,12 @@
1616

1717
package org.openapitools.codegen;
1818

19+
import io.swagger.annotations.Api;
1920
import io.swagger.v3.oas.models.OpenAPI;
2021
import io.swagger.v3.oas.models.PathItem;
2122
import io.swagger.v3.oas.models.media.*;
2223

24+
import io.swagger.v3.oas.models.responses.ApiResponse;
2325
import org.openapitools.codegen.utils.ModelUtils;
2426
import org.testng.annotations.Test;
2527

@@ -549,7 +551,7 @@ public void testSetPrimitiveTypesToNullable() {
549551
}
550552

551553
@Test
552-
public void testOpenAPINormalizerSimplifyOneOfAnyOf31SpecForIssue18184 () {
554+
public void testOpenAPINormalizerSimplifyOneOfAnyOf31SpecForIssue18184() {
553555
// to test the rule SIMPLIFY_ONEOF_ANYOF in 3.1 spec
554556
OpenAPI openAPI = TestUtils.parseSpec("src/test/resources/3_1/issue_18184.yaml");
555557
// test spec contains anyOf with a ref to enum and another scheme type is null
@@ -794,4 +796,22 @@ public void testOpenAPINormalizerProcessingAllOfSchema31Spec() {
794796
assertEquals(((Schema) schema2.getProperties().get("property2")).getAllOf(), null);
795797
assertEquals(((Schema) schema2.getProperties().get("property2")).getAllOf(), null);
796798
}
799+
800+
@Test
801+
public void testOpenAPINormalizerComponentsResponses31Spec() {
802+
OpenAPI openAPI = TestUtils.parseSpec("src/test/resources/3_1/common-parameters.yaml");
803+
ApiResponse apiResponse = openAPI.getComponents().getResponses().get("JustAnotherResponse");
804+
assertEquals(((Schema) apiResponse.getContent().get("application/json").getSchema().getProperties().get("uuid")).getType(), null);
805+
assertEquals(((Schema) apiResponse.getContent().get("application/json").getSchema().getProperties().get("label")).getType(), null);
806+
807+
Map<String, String> inputRules = Map.of(
808+
"NORMALIZE_31SPEC", "true"
809+
);
810+
OpenAPINormalizer openAPINormalizer = new OpenAPINormalizer(openAPI, inputRules);
811+
openAPINormalizer.normalize();
812+
813+
ApiResponse apiResponse2 = openAPI.getComponents().getResponses().get("JustAnotherResponse");
814+
assertEquals(((Schema) apiResponse2.getContent().get("application/json").getSchema().getProperties().get("uuid")).getType(), "integer");
815+
assertEquals(((Schema) apiResponse2.getContent().get("application/json").getSchema().getProperties().get("label")).getType(), "string");
816+
}
797817
}

modules/openapi-generator/src/test/resources/3_0/inline_model_resolver.yaml

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -455,6 +455,18 @@ paths:
455455
type: string
456456
components:
457457
requestBodies: {}
458+
responses:
459+
JustAnotherResponse:
460+
description: just another response
461+
content:
462+
application/json:
463+
schema:
464+
type: object
465+
properties:
466+
uuid:
467+
type: integer
468+
label:
469+
type: string
458470
schemas:
459471
Users:
460472
type: array

modules/openapi-generator/src/test/resources/3_1/common-parameters.yaml

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,6 +76,18 @@ paths:
7676
security:
7777
- api_key: []
7878
components:
79+
responses:
80+
JustAnotherResponse:
81+
description: JustAnotherResponse
82+
content:
83+
application/json:
84+
schema:
85+
type: object
86+
properties:
87+
uuid:
88+
type: integer
89+
label:
90+
type: string
7991
requestBodies:
8092
Pet:
8193
content:

0 commit comments

Comments
 (0)