From ea3fabfc976acc50761d5e74e253e2a0ec082609 Mon Sep 17 00:00:00 2001 From: Chris Gual Date: Thu, 17 Jul 2025 10:16:14 -0700 Subject: [PATCH 1/6] [kotlin-spring] add a Spring type converter for enum values #21564 --- .../languages/KotlinSpringServerCodegen.java | 20 ++++ .../kotlin-spring/converter.mustache | 31 ++++++ .../spring/KotlinSpringServerCodegenTest.java | 100 ++++++++++++++++++ 3 files changed, 151 insertions(+) create mode 100644 modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache diff --git a/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java b/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java index 995c05ae1a1a..12a6e870b035 100644 --- a/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java +++ b/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java @@ -20,6 +20,7 @@ import com.samskivert.mustache.Mustache; import com.samskivert.mustache.Mustache.Lambda; import com.samskivert.mustache.Template; +import io.swagger.v3.oas.models.Components; import io.swagger.v3.oas.models.OpenAPI; import io.swagger.v3.oas.models.Operation; import lombok.Getter; @@ -768,6 +769,11 @@ public void addOperationToGroup(String tag, String resourcePath, Operation opera public void preprocessOpenAPI(OpenAPI openAPI) { super.preprocessOpenAPI(openAPI); + if (SPRING_BOOT.equals(library) && containsEnums()) { + supportingFiles.add(new SupportingFile("converter.mustache", + (sourceFolder + File.separator + configPackage).replace(".", java.io.File.separator), "EnumConverterConfiguration.kt")); + } + if (!additionalProperties.containsKey(TITLE)) { // The purpose of the title is for: // - README documentation @@ -797,6 +803,20 @@ public void preprocessOpenAPI(OpenAPI openAPI) { // TODO: Handle tags } + private boolean containsEnums() { + if (openAPI == null) { + return false; + } + + Components components = this.openAPI.getComponents(); + if (components == null || components.getSchemas() == null) { + return false; + } + + return components.getSchemas().values().stream() + .anyMatch(it -> it.getEnum() != null && !it.getEnum().isEmpty()); + } + @Override public void postProcessModelProperty(CodegenModel model, CodegenProperty property) { super.postProcessModelProperty(model, property); diff --git a/modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache b/modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache new file mode 100644 index 000000000000..c41074e13db2 --- /dev/null +++ b/modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache @@ -0,0 +1,31 @@ +package {{configPackage}} + +{{#models}} + {{#model}} + {{#isEnum}} +import {{modelPackage}}.{{classname}} + {{/isEnum}} + {{/model}} +{{/models}} + +import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.Configuration +import org.springframework.core.convert.converter.Converter + +@Configuration(value = "{{configPackage}}.enumConverterConfiguration") +class EnumConverterConfiguration { + +{{#models}} +{{#model}} +{{#isEnum}} + @Bean(name = ["{{configPackage}}.EnumConverterConfiguration.{{classVarName}}Converter"]) + fun {{classVarName}}Converter(): Converter<{{{dataType}}}, {{classname}}> { + return object: Converter<{{{dataType}}}, {{classname}}> { + override fun convert(source: {{{dataType}}}): {{classname}} = {{classname}}.forValue(source) + } + } +{{/isEnum}} +{{/model}} +{{/models}} + +} diff --git a/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java b/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java index ba7b73e78ee5..883ef7c1adec 100644 --- a/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java +++ b/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java @@ -5,6 +5,8 @@ import io.swagger.v3.oas.models.info.Info; import io.swagger.v3.oas.models.servers.Server; import io.swagger.v3.parser.core.models.ParseOptions; +import java.util.HashMap; +import java.util.function.Consumer; import org.apache.commons.io.FileUtils; import org.assertj.core.api.Assertions; import org.jetbrains.annotations.NotNull; @@ -12,6 +14,8 @@ import org.openapitools.codegen.CodegenConstants; import org.openapitools.codegen.DefaultGenerator; import org.openapitools.codegen.TestUtils; +import org.openapitools.codegen.config.CodegenConfigurator; +import org.openapitools.codegen.java.assertions.JavaFileAssert; import org.openapitools.codegen.kotlin.KotlinTestUtils; import org.openapitools.codegen.languages.KotlinSpringServerCodegen; import org.openapitools.codegen.languages.features.CXFServerFeatures; @@ -31,8 +35,10 @@ import java.util.function.Function; import java.util.stream.Collectors; +import static org.assertj.core.api.Assertions.assertThat; import static org.openapitools.codegen.TestUtils.assertFileContains; import static org.openapitools.codegen.TestUtils.assertFileNotContains; +import static org.openapitools.codegen.languages.SpringCodegen.SPRING_BOOT; import static org.openapitools.codegen.languages.features.DocumentationProviderFeatures.ANNOTATION_LIBRARY; import static org.openapitools.codegen.languages.features.DocumentationProviderFeatures.DOCUMENTATION_PROVIDER; @@ -748,6 +754,49 @@ public void useBeanValidationGenerateAnnotationsForRequestBody() throws IOExcept ); } + @Test + public void contractWithoutEnumDoesNotContainEnumConverter() throws IOException { + Map output = generateFromContract("src/test/resources/3_0/generic.yaml"); + + assertThat(output).doesNotContainKey("EnumConverterConfiguration.kt"); + } + + @Test + public void contractWithEnumContainsEnumConverter() throws IOException { + Map output = generateFromContract("src/test/resources/3_0/enum.yaml"); + + File enumConverterFile = output.get("EnumConverterConfiguration.kt"); + assertThat(enumConverterFile).isNotNull(); + assertFileContains(enumConverterFile.toPath(), "fun typeConverter(): Converter {"); + assertFileContains(enumConverterFile.toPath(), "return object: Converter {"); + assertFileContains(enumConverterFile.toPath(), "override fun convert(source: kotlin.String): Type = Type.forValue(source)"); + } + + @Test + public void contractWithResolvedInnerEnumContainsEnumConverter() throws IOException { + File output = Files.createTempDirectory("test").toFile(); + output.deleteOnExit(); + + final CodegenConfigurator configurator = new CodegenConfigurator() + .setGeneratorName("kotlin-spring") + .setInputSpec("src/test/resources/3_0/inner_enum.yaml") + .addInlineSchemaOption("RESOLVE_INLINE_ENUMS", "true") + .setOutputDir(output.getAbsolutePath().replace("\\", "/")); + + final ClientOptInput clientOptInput = configurator.toClientOptInput(); + DefaultGenerator generator = new DefaultGenerator(); + generator.setGenerateMetadata(false); + + Map files = generator.opts(clientOptInput).generate().stream() + .collect(Collectors.toMap(File::getName, Function.identity())); + + File enumConverterFile = files.get("EnumConverterConfiguration.kt"); + assertThat(enumConverterFile).isNotNull(); + assertFileContains(enumConverterFile.toPath(), "fun ponyTypeConverter(): Converter {"); + assertFileContains(enumConverterFile.toPath(), "return object: Converter {"); + assertFileContains(enumConverterFile.toPath(), "override fun convert(source: kotlin.String): PonyType = PonyType.forValue(source)"); + } + @Test public void givenMultipartFormArray_whenGenerateDelegateAndService_thenParameterIsCreatedAsListOfMultipartFile() throws IOException { File output = Files.createTempDirectory("test").toFile().getCanonicalFile(); @@ -1192,4 +1241,55 @@ public void testValidationsInQueryParams_issue21238_Api_Delegate() throws IOExce "@NotNull", "@Valid", "@Pattern(regexp=\"^[a-zA-Z0-9]+[a-zA-Z0-9\\\\.\\\\-_]*[a-zA-Z0-9]+$\")"); } + + private Map generateFromContract(String url) throws IOException { + return generateFromContract(url, new HashMap<>(), new HashMap<>()); + } + + private Map generateFromContract(String url, Map additionalProperties) throws IOException { + return generateFromContract(url, additionalProperties, new HashMap<>()); + } + + private Map generateFromContract( + String url, + Map additionalProperties, + Map generatorPropertyDefaults + ) throws IOException { + return generateFromContract(url, additionalProperties, generatorPropertyDefaults, codegen -> { + }); + } + + /** + * Generate the contract with additional configuration. + *

+ * use CodegenConfigurator instead of CodegenConfig for easier configuration like in JavaClientCodeGenTest + */ + private Map generateFromContract( + String url, + Map additionalProperties, + Map generatorPropertyDefaults, + Consumer consumer + ) throws IOException { + + File output = Files.createTempDirectory("test").toFile().getCanonicalFile(); + output.deleteOnExit(); + + final CodegenConfigurator configurator = new CodegenConfigurator() + .setGeneratorName("kotlin-spring") + .setAdditionalProperties(additionalProperties) + .setValidateSpec(false) + .setInputSpec(url) + .setLibrary(SPRING_BOOT) + .setOutputDir(output.getAbsolutePath()); + + consumer.accept(configurator); + + ClientOptInput input = configurator.toClientOptInput(); + DefaultGenerator generator = new DefaultGenerator(); + generator.setGenerateMetadata(false); + generatorPropertyDefaults.forEach(generator::setGeneratorPropertyDefault); + + return generator.opts(input).generate().stream() + .collect(Collectors.toMap(File::getName, Function.identity())); + } } From fc8ec1a03880e6369d86cad268e19c240d0e94bb Mon Sep 17 00:00:00 2001 From: Chris Gual Date: Thu, 17 Jul 2025 10:33:41 -0700 Subject: [PATCH 2/6] [kotlin-spring] simplify unit test for inner enum converter --- .../spring/KotlinSpringServerCodegenTest.java | 22 +++++-------------- 1 file changed, 6 insertions(+), 16 deletions(-) diff --git a/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java b/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java index 883ef7c1adec..5a0d24cdcf1a 100644 --- a/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java +++ b/modules/openapi-generator/src/test/java/org/openapitools/codegen/kotlin/spring/KotlinSpringServerCodegenTest.java @@ -774,21 +774,12 @@ public void contractWithEnumContainsEnumConverter() throws IOException { @Test public void contractWithResolvedInnerEnumContainsEnumConverter() throws IOException { - File output = Files.createTempDirectory("test").toFile(); - output.deleteOnExit(); - - final CodegenConfigurator configurator = new CodegenConfigurator() - .setGeneratorName("kotlin-spring") - .setInputSpec("src/test/resources/3_0/inner_enum.yaml") - .addInlineSchemaOption("RESOLVE_INLINE_ENUMS", "true") - .setOutputDir(output.getAbsolutePath().replace("\\", "/")); - - final ClientOptInput clientOptInput = configurator.toClientOptInput(); - DefaultGenerator generator = new DefaultGenerator(); - generator.setGenerateMetadata(false); - - Map files = generator.opts(clientOptInput).generate().stream() - .collect(Collectors.toMap(File::getName, Function.identity())); + Map files = generateFromContract( + "src/test/resources/3_0/inner_enum.yaml", + new HashMap<>(), + new HashMap<>(), + configurator -> configurator.addInlineSchemaOption("RESOLVE_INLINE_ENUMS", "true") + ); File enumConverterFile = files.get("EnumConverterConfiguration.kt"); assertThat(enumConverterFile).isNotNull(); @@ -1241,7 +1232,6 @@ public void testValidationsInQueryParams_issue21238_Api_Delegate() throws IOExce "@NotNull", "@Valid", "@Pattern(regexp=\"^[a-zA-Z0-9]+[a-zA-Z0-9\\\\.\\\\-_]*[a-zA-Z0-9]+$\")"); } - private Map generateFromContract(String url) throws IOException { return generateFromContract(url, new HashMap<>(), new HashMap<>()); } From 493d2d09dab92f5749e3d74c4e30955c296ef17a Mon Sep 17 00:00:00 2001 From: Chris Gual Date: Thu, 17 Jul 2025 12:37:57 -0700 Subject: [PATCH 3/6] update samples --- .../.openapi-generator/FILES | 1 + .../EnumConverterConfiguration.kt | 19 +++++++++++++++++++ .../.openapi-generator/FILES | 1 + .../EnumConverterConfiguration.kt | 19 +++++++++++++++++++ 4 files changed, 40 insertions(+) create mode 100644 samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt create mode 100644 samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt diff --git a/samples/server/petstore/kotlin-springboot-integer-enum/.openapi-generator/FILES b/samples/server/petstore/kotlin-springboot-integer-enum/.openapi-generator/FILES index 97df5ba6fbbc..d35b88d1309a 100644 --- a/samples/server/petstore/kotlin-springboot-integer-enum/.openapi-generator/FILES +++ b/samples/server/petstore/kotlin-springboot-integer-enum/.openapi-generator/FILES @@ -9,5 +9,6 @@ settings.gradle src/main/kotlin/org/openapitools/api/ApiUtil.kt src/main/kotlin/org/openapitools/api/DefaultApi.kt src/main/kotlin/org/openapitools/api/Exceptions.kt +src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt src/main/kotlin/org/openapitools/model/ApiError.kt src/main/kotlin/org/openapitools/model/ReasonCode.kt diff --git a/samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt b/samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt new file mode 100644 index 000000000000..e40ce24571d9 --- /dev/null +++ b/samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt @@ -0,0 +1,19 @@ +package org.openapitools.configuration + +import org.openapitools.model.ReasonCode + +import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.Configuration +import org.springframework.core.convert.converter.Converter + +@Configuration(value = "org.openapitools.configuration.enumConverterConfiguration") +class EnumConverterConfiguration { + + @Bean(name = ["org.openapitools.configuration.EnumConverterConfiguration.reasonCodeConverter"]) + fun reasonCodeConverter(): Converter { + return object: Converter { + override fun convert(source: kotlin.Int): ReasonCode = ReasonCode.forValue(source) + } + } + +} diff --git a/samples/server/petstore/kotlin-springboot-multipart-request-model/.openapi-generator/FILES b/samples/server/petstore/kotlin-springboot-multipart-request-model/.openapi-generator/FILES index 24c5ef9ccc87..2ea9e1431b36 100644 --- a/samples/server/petstore/kotlin-springboot-multipart-request-model/.openapi-generator/FILES +++ b/samples/server/petstore/kotlin-springboot-multipart-request-model/.openapi-generator/FILES @@ -12,6 +12,7 @@ src/main/kotlin/org/openapitools/SpringDocConfiguration.kt src/main/kotlin/org/openapitools/api/ApiUtil.kt src/main/kotlin/org/openapitools/api/Exceptions.kt src/main/kotlin/org/openapitools/api/MultipartMixedApiController.kt +src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt src/main/kotlin/org/openapitools/model/MultipartMixedRequestMarker.kt src/main/kotlin/org/openapitools/model/MultipartMixedStatus.kt src/main/resources/application.yaml diff --git a/samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt b/samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt new file mode 100644 index 000000000000..15433781d33e --- /dev/null +++ b/samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt @@ -0,0 +1,19 @@ +package org.openapitools.configuration + +import org.openapitools.model.MultipartMixedStatus + +import org.springframework.context.annotation.Bean +import org.springframework.context.annotation.Configuration +import org.springframework.core.convert.converter.Converter + +@Configuration(value = "org.openapitools.configuration.enumConverterConfiguration") +class EnumConverterConfiguration { + + @Bean(name = ["org.openapitools.configuration.EnumConverterConfiguration.multipartMixedStatusConverter"]) + fun multipartMixedStatusConverter(): Converter { + return object: Converter { + override fun convert(source: kotlin.String): MultipartMixedStatus = MultipartMixedStatus.forValue(source) + } + } + +} From 9a6a0b5a35d987537b10eb41303657f6d73e37b7 Mon Sep 17 00:00:00 2001 From: Chris Gual Date: Sat, 19 Jul 2025 19:52:28 -0700 Subject: [PATCH 4/6] code review feedback; move containsEnums to ModelUtils --- .../languages/KotlinSpringServerCodegen.java | 17 ++--------------- .../codegen/languages/SpringCodegen.java | 18 ++---------------- .../openapitools/codegen/utils/ModelUtils.java | 13 +++++++++++++ 3 files changed, 17 insertions(+), 31 deletions(-) diff --git a/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java b/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java index 12a6e870b035..14f5faba4946 100644 --- a/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java +++ b/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/KotlinSpringServerCodegen.java @@ -34,6 +34,7 @@ import org.openapitools.codegen.model.ModelsMap; import org.openapitools.codegen.model.OperationMap; import org.openapitools.codegen.model.OperationsMap; +import org.openapitools.codegen.utils.ModelUtils; import org.openapitools.codegen.utils.URLPathUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -769,7 +770,7 @@ public void addOperationToGroup(String tag, String resourcePath, Operation opera public void preprocessOpenAPI(OpenAPI openAPI) { super.preprocessOpenAPI(openAPI); - if (SPRING_BOOT.equals(library) && containsEnums()) { + if (SPRING_BOOT.equals(library) && ModelUtils.containsEnums(this.openAPI)) { supportingFiles.add(new SupportingFile("converter.mustache", (sourceFolder + File.separator + configPackage).replace(".", java.io.File.separator), "EnumConverterConfiguration.kt")); } @@ -803,20 +804,6 @@ public void preprocessOpenAPI(OpenAPI openAPI) { // TODO: Handle tags } - private boolean containsEnums() { - if (openAPI == null) { - return false; - } - - Components components = this.openAPI.getComponents(); - if (components == null || components.getSchemas() == null) { - return false; - } - - return components.getSchemas().values().stream() - .anyMatch(it -> it.getEnum() != null && !it.getEnum().isEmpty()); - } - @Override public void postProcessModelProperty(CodegenModel model, CodegenProperty property) { super.postProcessModelProperty(model, property); diff --git a/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/SpringCodegen.java b/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/SpringCodegen.java index 621c91bfa84f..76be2f1f3791 100644 --- a/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/SpringCodegen.java +++ b/modules/openapi-generator/src/main/java/org/openapitools/codegen/languages/SpringCodegen.java @@ -18,7 +18,6 @@ package org.openapitools.codegen.languages; import com.samskivert.mustache.Mustache; -import io.swagger.v3.oas.models.Components; import io.swagger.v3.oas.models.OpenAPI; import io.swagger.v3.oas.models.Operation; import io.swagger.v3.oas.models.PathItem; @@ -40,6 +39,7 @@ import org.openapitools.codegen.templating.mustache.SplitStringLambda; import org.openapitools.codegen.templating.mustache.SpringHttpStatusLambda; import org.openapitools.codegen.templating.mustache.TrimWhitespaceLambda; +import org.openapitools.codegen.utils.ModelUtils; import org.openapitools.codegen.utils.ProcessUtils; import org.openapitools.codegen.utils.URLPathUtils; import org.slf4j.Logger; @@ -648,20 +648,6 @@ public void processOpts() { supportsAdditionalPropertiesWithComposedSchema = true; } - private boolean containsEnums() { - if (openAPI == null) { - return false; - } - - Components components = this.openAPI.getComponents(); - if (components == null || components.getSchemas() == null) { - return false; - } - - return components.getSchemas().values().stream() - .anyMatch(it -> it.getEnum() != null && !it.getEnum().isEmpty()); - } - private boolean supportLibraryUseTags() { return SPRING_BOOT.equals(library) || SPRING_CLOUD_LIBRARY.equals(library); } @@ -696,7 +682,7 @@ public void addOperationToGroup(String tag, String resourcePath, Operation opera public void preprocessOpenAPI(OpenAPI openAPI) { super.preprocessOpenAPI(openAPI); - if (SPRING_BOOT.equals(library) && containsEnums()) { + if (SPRING_BOOT.equals(library) && ModelUtils.containsEnums(this.openAPI)) { supportingFiles.add(new SupportingFile("converter.mustache", (sourceFolder + File.separator + configPackage).replace(".", java.io.File.separator), "EnumConverterConfiguration.java")); } diff --git a/modules/openapi-generator/src/main/java/org/openapitools/codegen/utils/ModelUtils.java b/modules/openapi-generator/src/main/java/org/openapitools/codegen/utils/ModelUtils.java index 405934531f01..2c79c8a6ca83 100644 --- a/modules/openapi-generator/src/main/java/org/openapitools/codegen/utils/ModelUtils.java +++ b/modules/openapi-generator/src/main/java/org/openapitools/codegen/utils/ModelUtils.java @@ -2435,6 +2435,19 @@ public static boolean isMetadataOnlySchema(Schema schema) { schema.getContentSchema() != null); } + /** + * Returns true if the OpenAPI specification contains any schemas which are enums. + * @param openAPI OpenAPI specification + * @return true if the OpenAPI specification contains any schemas which are enums. + */ + public static boolean containsEnums(OpenAPI openAPI) { + Map schemaMap = getSchemas(openAPI); + if (schemaMap.isEmpty()) { + return false; + } + + return schemaMap.values().stream().anyMatch(ModelUtils::isEnumSchema); + } @FunctionalInterface private interface OpenAPISchemaVisitor { From 64ce1af89056d89d55e7ba65a89cc335ff354080 Mon Sep 17 00:00:00 2001 From: Chris Gual Date: Sun, 20 Jul 2025 08:50:44 -0700 Subject: [PATCH 5/6] code review feedback; provide comment for generated EnumConverterConfiguration.kt --- .../src/main/resources/kotlin-spring/converter.mustache | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache b/modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache index c41074e13db2..acdd13073fcb 100644 --- a/modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache +++ b/modules/openapi-generator/src/main/resources/kotlin-spring/converter.mustache @@ -12,6 +12,13 @@ import org.springframework.context.annotation.Bean import org.springframework.context.annotation.Configuration import org.springframework.core.convert.converter.Converter +/** + * This class provides Spring Converter beans for the enum models in the OpenAPI specification. + * + * By default, Spring only converts primitive types to enums using Enum::valueOf, which can prevent + * correct conversion if the OpenAPI specification is using an `enumPropertyNaming` other than + * `original` or the specification has an integer enum. + */ @Configuration(value = "{{configPackage}}.enumConverterConfiguration") class EnumConverterConfiguration { From 2af405dd2199dc8880cd30b5258798173adae232 Mon Sep 17 00:00:00 2001 From: Chris Gual Date: Sun, 20 Jul 2025 09:27:03 -0700 Subject: [PATCH 6/6] update samples --- .../configuration/EnumConverterConfiguration.kt | 7 +++++++ .../configuration/EnumConverterConfiguration.kt | 7 +++++++ 2 files changed, 14 insertions(+) diff --git a/samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt b/samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt index e40ce24571d9..8d2f1d585482 100644 --- a/samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt +++ b/samples/server/petstore/kotlin-springboot-integer-enum/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt @@ -6,6 +6,13 @@ import org.springframework.context.annotation.Bean import org.springframework.context.annotation.Configuration import org.springframework.core.convert.converter.Converter +/** + * This class provides Spring Converter beans for the enum models in the OpenAPI specification. + * + * By default, Spring only converts primitive types to enums using Enum::valueOf, which can prevent + * correct conversion if the OpenAPI specification is using an `enumPropertyNaming` other than + * `original` or the specification has an integer enum. + */ @Configuration(value = "org.openapitools.configuration.enumConverterConfiguration") class EnumConverterConfiguration { diff --git a/samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt b/samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt index 15433781d33e..5aff967ce622 100644 --- a/samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt +++ b/samples/server/petstore/kotlin-springboot-multipart-request-model/src/main/kotlin/org/openapitools/configuration/EnumConverterConfiguration.kt @@ -6,6 +6,13 @@ import org.springframework.context.annotation.Bean import org.springframework.context.annotation.Configuration import org.springframework.core.convert.converter.Converter +/** + * This class provides Spring Converter beans for the enum models in the OpenAPI specification. + * + * By default, Spring only converts primitive types to enums using Enum::valueOf, which can prevent + * correct conversion if the OpenAPI specification is using an `enumPropertyNaming` other than + * `original` or the specification has an integer enum. + */ @Configuration(value = "org.openapitools.configuration.enumConverterConfiguration") class EnumConverterConfiguration {