[test-stack] Implement inner class assertion and fix typo "doesNotContains" (#18921)

* Implement InnerClassAssert for easy inner class testing

* Suppress "'Optional.get()' without 'isPresent()' check" warning

For now, until https://youtrack.jetbrains.com/issue/IDEA-354935
is solved.

* Apply DRY refactoring

* Move newTempFolder helper method into TestUtils

* Fix typo `doesNotContains`

* Pluralize assertion classes that extend ListAssert

* Add short-hand has/doesNotHaveAnnotation methods to Method assertions

So .hasAssertion(String) can replace .assertMethodAnnotations().containsWithName(String)

* Refactor tests, simplifying setup using CodegenConfigurator

* Harmonize API, removing confusion between has… and assert…

This makes our the assertion API more consistent, in the way that
assertSomething("") will always return a different assertion type,
while hasSomething("") will always return the same type.

* Use simplified hasAnnotation/doesNotHaveAnnotation assertions
This commit is contained in:
Philzen 2024-06-16 04:03:11 +02:00 committed by GitHub
parent 3d93862c6d
commit ec8998b39f
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
26 changed files with 1202 additions and 1086 deletions

View File

@ -2592,9 +2592,9 @@ public class DefaultCodegenTest {
DefaultGenerator generator = new DefaultGenerator();
List<File> files = generator.opts(clientOptInput).generate();
TestUtils.ensureDoesNotContainsFile(files, output, "src/main/java/org/openapitools/client/model/FreeFormWithValidation.java");
TestUtils.ensureDoesNotContainsFile(files, output, "src/main/java/org/openapitools/client/model/FreeFormInterface.java");
TestUtils.ensureDoesNotContainsFile(files, output, "src/main/java/org/openapitools/client/model/FreeForm.java");
TestUtils.ensureDoesNotContainFile(files, output, "src/main/java/org/openapitools/client/model/FreeFormWithValidation.java");
TestUtils.ensureDoesNotContainFile(files, output, "src/main/java/org/openapitools/client/model/FreeFormInterface.java");
TestUtils.ensureDoesNotContainFile(files, output, "src/main/java/org/openapitools/client/model/FreeForm.java");
output.deleteOnExit();
}

View File

@ -86,29 +86,29 @@ public class DefaultGeneratorTest {
TestUtils.ensureContainsFile(files, output, "build.gradle");
Assert.assertTrue(new File(output, "build.gradle").exists());
TestUtils.ensureDoesNotContainsFile(files, output, "api/openapi.yaml");
TestUtils.ensureDoesNotContainFile(files, output, "api/openapi.yaml");
Assert.assertFalse(new File(output, "api").exists());
TestUtils.ensureDoesNotContainsFile(files, output, ".github/workflows/");
TestUtils.ensureDoesNotContainFile(files, output, ".github/workflows/");
Assert.assertFalse(new File(output, ".github").exists());
// Check excluded files
TestUtils.ensureDoesNotContainsFile(files, output, ".travis.yml");
TestUtils.ensureDoesNotContainFile(files, output, ".travis.yml");
Assert.assertFalse(new File(output, ".travis.yml").exists());
TestUtils.ensureDoesNotContainsFile(files, output, "build.sbt");
TestUtils.ensureDoesNotContainFile(files, output, "build.sbt");
Assert.assertFalse(new File(output, "build.sbt").exists());
TestUtils.ensureDoesNotContainsFile(files, output, "src/main/AndroidManifest.xml");
TestUtils.ensureDoesNotContainFile(files, output, "src/main/AndroidManifest.xml");
Assert.assertFalse(new File(output, "src/main/AndroidManifest.xml").exists());
TestUtils.ensureDoesNotContainsFile(files, output, "pom.xml");
TestUtils.ensureDoesNotContainFile(files, output, "pom.xml");
Assert.assertFalse(new File(output, "pom.xml").exists());
TestUtils.ensureDoesNotContainsFile(files, output, "src/test/java/org/openapitools/client/model/CategoryTest.java");
TestUtils.ensureDoesNotContainFile(files, output, "src/test/java/org/openapitools/client/model/CategoryTest.java");
Assert.assertFalse(new File(output, "src/test/java/org/openapitools/client/model/CategoryTest.java").exists());
TestUtils.ensureDoesNotContainsFile(files, output, "src/main/java/org/openapitools/client/api/UserApi.java");
TestUtils.ensureDoesNotContainFile(files, output, "src/main/java/org/openapitools/client/api/UserApi.java");
Assert.assertFalse(new File(output, "src/main/java/org/openapitools/client/api/UserApi.java").exists());
} finally {
output.deleteOnExit();
@ -162,7 +162,7 @@ public class DefaultGeneratorTest {
TestUtils.ensureContainsFile(files, output, "src/main/java/org/openapitools/client/api/PetApi.java");
Assert.assertTrue(new File(output, "src/main/java/org/openapitools/client/api/PetApi.java").exists());
TestUtils.ensureDoesNotContainsFile(files, output, apiTestRelativePath);
TestUtils.ensureDoesNotContainFile(files, output, apiTestRelativePath);
Assert.assertTrue(apiTestFile.exists());
String apiTestContents = Files.readAllLines(apiTestFile.toPath()).get(0);
Assert.assertEquals(apiTestContents, "empty", "Expected test file to retain original contents.");
@ -171,7 +171,7 @@ public class DefaultGeneratorTest {
TestUtils.ensureContainsFile(files, output, "src/main/java/org/openapitools/client/model/Category.java");
Assert.assertTrue(new File(output, "src/test/java/org/openapitools/client/model/CategoryTest.java").exists());
TestUtils.ensureDoesNotContainsFile(files, output, modelTestRelativePath);
TestUtils.ensureDoesNotContainFile(files, output, modelTestRelativePath);
Assert.assertTrue(modelTestFile.exists());
String modelTestContents = Files.readAllLines(modelTestFile.toPath()).get(0);
Assert.assertEquals(modelTestContents, "empty", "Expected test file to retain original contents.");
@ -827,19 +827,19 @@ public class DefaultGeneratorTest {
// Check not generated cause backwards compatibility files
String ft1FileName = "src/main/java/org/openapitools/model/FT1.java";
TestUtils.ensureDoesNotContainsFile(files, output, ft1FileName);
TestUtils.ensureDoesNotContainFile(files, output, ft1FileName);
Assert.assertFalse(new File(output, ft1FileName).exists());
String ft2FileName = "src/main/java/org/openapitools/model/FT2.java";
TestUtils.ensureDoesNotContainsFile(files, output, ft2FileName);
TestUtils.ensureDoesNotContainFile(files, output, ft2FileName);
Assert.assertFalse(new File(output, ft2FileName).exists());
String ft3FileName = "src/main/java/org/openapitools/model/FT3.java";
TestUtils.ensureDoesNotContainsFile(files, output, ft3FileName);
TestUtils.ensureDoesNotContainFile(files, output, ft3FileName);
Assert.assertFalse(new File(output, ft3FileName).exists());
String bttFileName = "src/main/java/org/openapitools/model/BTT.java";
TestUtils.ensureDoesNotContainsFile(files, output, bttFileName);
TestUtils.ensureDoesNotContainFile(files, output, bttFileName);
Assert.assertFalse(new File(output, bttFileName).exists());
} finally {

View File

@ -98,7 +98,7 @@ public class TestUtils {
assertTrue(generatedFiles.contains(path.toFile()), "File '" + path.toAbsolutePath() + "' was not found in the list of generated files");
}
public static void ensureDoesNotContainsFile(List<File> generatedFiles, File root, String filename) {
public static void ensureDoesNotContainFile(List<File> generatedFiles, File root, String filename) {
Path path = root.toPath().resolve(filename);
assertFalse(generatedFiles.contains(path.toFile()), "File '" + path.toAbsolutePath() + "' was found in the list of generated files");
}
@ -217,7 +217,7 @@ public class TestUtils {
.containsWithName("javax.persistence.Entity")
.containsWithNameAndAttributes("javax.persistence.Table", ImmutableMap.of("name", "\"employees\""))
.toType()
.hasProperty("assignments")
.assertProperty("assignments")
.assertPropertyAnnotations()
.containsWithNameAndAttributes("javax.persistence.OneToMany", ImmutableMap.of("mappedBy", "\"employee\""))
.toProperty()
@ -227,17 +227,17 @@ public class TestUtils {
.assertTypeAnnotations()
.containsWithName("javax.persistence.MappedSuperclass")
.toType()
.hasProperty("id")
.assertProperty("id")
.assertPropertyAnnotations()
.containsWithName("javax.persistence.Id")
.toProperty()
.toType()
.hasProperty("email")
.assertProperty("email")
.assertPropertyAnnotations()
.containsWithName("org.hibernate.annotations.Formula")
.toProperty()
.toType()
.hasProperty("hasAcceptedTerms")
.assertProperty("hasAcceptedTerms")
.assertPropertyAnnotations()
.containsWithName("javax.persistence.Transient")
.toProperty()
@ -248,13 +248,13 @@ public class TestUtils {
.containsWithName("javax.persistence.Entity")
.containsWithNameAndAttributes("javax.persistence.Table", ImmutableMap.of("name", "\"survey_groups\""))
.toType()
.hasProperty("assignments")
.assertProperty("assignments")
.assertPropertyAnnotations()
.containsWithName("javax.persistence.OneToMany")
.containsWithNameAndAttributes("javax.persistence.JoinColumn", ImmutableMap.of("name", "\"survey_group_id\""))
.toProperty()
.toType()
.hasProperty("disabled")
.assertProperty("disabled")
.assertPropertyAnnotations()
.containsWithNameAndAttributes("javax.persistence.Column", ImmutableMap.of("nullable", "false"))
.toProperty()
@ -265,7 +265,7 @@ public class TestUtils {
.containsWithName("javax.persistence.MappedSuperclass")
.containsWithName("javax.persistence.EntityListeners")
.toType()
.hasProperty("id")
.assertProperty("id")
.assertPropertyAnnotations()
.containsWithName("javax.persistence.Id")
.containsWithNameAndAttributes("javax.persistence.GeneratedValue", ImmutableMap.of("generator", "\"UUID\""))
@ -273,39 +273,39 @@ public class TestUtils {
.containsWithNameAndAttributes("javax.persistence.Column", ImmutableMap.of("name", "\"id\"","updatable", "false","nullable", "false"))
.toProperty()
.toType()
.hasProperty("createdDate")
.assertProperty("createdDate")
.assertPropertyAnnotations()
.containsWithName("org.springframework.data.annotation.CreatedDate")
.toProperty()
.toType()
.hasProperty("createdBy")
.assertProperty("createdBy")
.assertPropertyAnnotations()
.containsWithName("org.springframework.data.annotation.CreatedBy")
.toProperty()
.toType()
.hasProperty("modifiedDate")
.assertProperty("modifiedDate")
.assertPropertyAnnotations()
.containsWithName("org.springframework.data.annotation.LastModifiedDate")
.toProperty()
.toType()
.hasProperty("modifiedBy")
.assertProperty("modifiedBy")
.assertPropertyAnnotations()
.containsWithName("org.springframework.data.annotation.LastModifiedBy")
.toProperty()
.toType()
.hasProperty("opportunityId")
.assertProperty("opportunityId")
.assertPropertyAnnotations()
.containsWithNameAndAttributes("javax.persistence.Column", ImmutableMap.of("unique", "true"))
.toProperty()
.toType()
.hasProperty("submissionStatus")
.assertProperty("submissionStatus")
.assertPropertyAnnotations()
.containsWithName("javax.persistence.Transient")
.toProperty()
.toType();
JavaFileAssert.assertThat(java.nio.file.Paths.get(baseOutputPath + "/CompanyDto.java"))
.hasProperty("priceCategory")
.assertProperty("priceCategory")
.assertPropertyAnnotations()
.containsWithNameAndAttributes("IgnoreForRoles", ImmutableMap.of("value", "\"MEDIA_ADMIN\""));
}
@ -319,4 +319,16 @@ public class TestUtils {
objs.setModels(modelMaps);
return objs;
}
public static Path newTempFolder() {
final Path tempDir;
try {
tempDir = Files.createTempDirectory("test");
} catch (IOException e) {
throw new RuntimeException(e);
}
tempDir.toFile().deleteOnExit();
return tempDir;
}
}

View File

@ -77,8 +77,8 @@ public class MergedSpecBuilderTest {
.assertMethodAnnotations()
.containsWithNameAndAttributes("RequestMapping", ImmutableMap.of("value", "\"/spec1/complex/{param1}/path\""))
.toMethod()
.hasParameter("param1")
.withType("String")
.assertParameter("param1")
.hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("PathVariable", ImmutableMap.of("value", "\"param1\""));
@ -92,4 +92,4 @@ public class MergedSpecBuilderTest {
.assertMethod("getSpec2Field").hasReturnType("BigDecimal");
}
}
}

View File

@ -60,6 +60,7 @@ import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.entry;
import static org.assertj.core.api.InstanceOfAssertFactories.FILE;
import static org.openapitools.codegen.CodegenConstants.SERIALIZATION_LIBRARY;
import static org.openapitools.codegen.TestUtils.newTempFolder;
import static org.openapitools.codegen.TestUtils.validateJavaSourceFiles;
import static org.openapitools.codegen.languages.JavaClientCodegen.*;
import static org.testng.Assert.*;
@ -1537,13 +1538,13 @@ public class JavaClientCodegenTest {
.stream().collect(Collectors.toMap(File::getName, Function.identity()));
JavaFileAssert.assertThat(files.get("DefaultValuesType.java"))
.hasProperty("stringDefault")
.assertProperty("stringDefault")
.asString().endsWith("= new ArrayList<>();");
JavaFileAssert.assertThat(files.get("DefaultValuesType.java"))
.hasProperty("stringDefault2")
.assertProperty("stringDefault2")
.asString().endsWith("= new ArrayList<>(Arrays.asList(\"Hallo\", \"Huhu\"));");
JavaFileAssert.assertThat(files.get("DefaultValuesType.java"))
.hasProperty("objectDefault")
.assertProperty("objectDefault")
.asString().endsWith("= new ArrayList<>();");
}
@ -1624,11 +1625,11 @@ public class JavaClientCodegenTest {
JavaFileAssert.assertThat(files.get("DefaultApi.java"))
.assertMethod("operationWithHttpInfo")
.hasParameter("requestBody")
.assertParameter("requestBody")
.assertParameterAnnotations()
.containsWithName("NotNull")
.toParameter().toMethod()
.hasParameter("xNonNullHeaderParameter")
.assertParameter("xNonNullHeaderParameter")
.assertParameterAnnotations()
.containsWithName("NotNull");
}
@ -2024,8 +2025,8 @@ public class JavaClientCodegenTest {
JavaFileAssert.assertThat(files.get("AbstractOpenApiSchema.java"))
.assertTypeAnnotations()
.doesNotContainsWithName("annotation1")
.doesNotContainsWithName("annotation2");
.doesNotContainWithName("annotation1")
.doesNotContainWithName("annotation2");
JavaFileAssert.assertThat(files.get("Animal.java"))
.assertTypeAnnotations()
.containsWithName("annotation1")
@ -2679,16 +2680,6 @@ public class JavaClientCodegenTest {
"com.fasterxml.jackson.databind.annotation.JsonSerialize"
);
}
static private Path newTempFolder() {
try {
var tempDir = Files.createTempDirectory("test");
tempDir.toFile().deleteOnExit();
return tempDir;
} catch (IOException e) {
throw new RuntimeException(e);
}
}
/**
* General XML annotations test (both JAXB and Jackson)
@ -2698,28 +2689,24 @@ public class JavaClientCodegenTest {
* - <a href="https://github.com/OpenAPITools/openapi-generator/issues/18869">Microprofile generator missing Jackson annotations and namespaces</a>
*/
@Test(dataProvider = "librariesSupportingJackson")
void shouldGenerateCorrectXmlAnnotations(Library library) throws IOException {
void shouldGenerateCorrectXmlAnnotations(Library library) {
// Arrange
final String TEST_SPEC = "src/test/resources/3_0/java/xml-annotations-test.yaml";
final Path output = newTempFolder();
JavaClientCodegen codegen = new JavaClientCodegen();
codegen.setLibrary(library.getValue());
codegen.setSerializationLibrary("jackson");
codegen.setWithXml(true);
codegen.setOutputDir(output.toString());
DefaultGenerator generator = new DefaultGenerator();
generator.setGeneratorPropertyDefault(CodegenConstants.MODELS, "true");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_TESTS, "false");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_DOCS, "false");
generator.setGenerateMetadata(false);
final CodegenConfigurator config = new CodegenConfigurator()
.addAdditionalProperty(CodegenConstants.WITH_XML, true)
.addAdditionalProperty(SERIALIZATION_LIBRARY, "jackson")
.addGlobalProperty(CodegenConstants.MODELS, "Pet")
.addGlobalProperty(CodegenConstants.MODEL_DOCS, null)
.addGlobalProperty(CodegenConstants.MODEL_TESTS, null)
.setGeneratorName("java")
.setInputSpec("src/test/resources/3_0/java/xml-annotations-test.yaml")
.setLibrary(library.value)
.setOutputDir(newTempFolder().toString());
// Act
generator.opts(new ClientOptInput().config(codegen).openAPI(TestUtils.parseSpec(TEST_SPEC))).generate();
final List<File> files = new DefaultGenerator().opts(config.toClientOptInput()).generate();
// Assert
JavaFileAssert.assertThat(output.resolve("src/main/java/org/openapitools/client/model/Pet.java").toFile())
JavaFileAssert.assertThat(files.get(0))
.assertTypeAnnotations()
.containsWithNameAndAttributes("XmlAccessorType", Map.of("value", "XmlAccessType.FIELD"))
.containsWithNameAndAttributes("XmlRootElement", Map.of("name", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
@ -2727,116 +2714,116 @@ public class JavaClientCodegenTest {
.toType()
// test custom-name on wrapper element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
.hasProperty("tags").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("tags").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Tag\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"TagList\""))
.toProperty().toType()
.assertMethod("getTags").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Tag\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"TagList\"", "useWrapping", "true"))
.toMethod().toFileAssert()
.assertMethod("getTags")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"Tag\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"TagList\"", "useWrapping", "true"))
.toFileAssert()
// custom internal xml-array element name, non-wrapped (1st example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("friends").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("friends").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"friend-pet\""))
.toProperty().toType()
.assertMethod("getFriends").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"friend-pet\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toMethod().toFileAssert()
.assertMethod("getFriends")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"friend-pet\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toFileAssert()
// test custom element name (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Change%20Element%20Names)
.hasProperty("status").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("status").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"PetStatus\""))
.toProperty().toType()
.assertMethod("getStatus").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"PetStatus\""))
.toMethod().toFileAssert()
.assertMethod("getStatus")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"PetStatus\""))
.toFileAssert()
// test same-name wrapping element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Wrapping%20Arrays)
// maps to 3rd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"photoUrls\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"photoUrls\""))
.toProperty().toType()
.assertMethod("getPhotoUrls").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"photoUrls\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"photoUrls\"", "useWrapping", "true"))
.toMethod().toFileAssert()
.assertMethod("getPhotoUrls")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"photoUrls\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"photoUrls\"", "useWrapping", "true"))
.toFileAssert()
// test attribute generation (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Convert%20Property%20to%20an%20Attribute)
.hasProperty("name").assertPropertyAnnotations()
.doesNotContainsWithName("XmlElement")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("name").assertPropertyAnnotations()
.doesNotContainWithName("XmlElement")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlAttribute", Map.of("name", "\"name\""))
.toProperty().toType()
.assertMethod("getName").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("isAttribute", "true", "localName", "\"name\""))
.toMethod().toFileAssert()
.assertMethod("getName")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("isAttribute", "true", "localName", "\"name\""))
.toFileAssert()
// test XML namespace and prefix (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Prefixes%20and%20Namespaces)
.hasProperty("id").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("id").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toProperty().toType()
.assertMethod("getId").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toMethod().toFileAssert()
.assertMethod("getId")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toFileAssert()
// external xml-array element name only (last example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("foods").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("foods").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"yummy-yummy\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"yummy-yummy\""))
.toProperty().toType()
.assertMethod("getFoods").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"yummy-yummy\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"yummy-yummy\""))
.toMethod().toFileAssert()
.assertMethod("getFoods")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"yummy-yummy\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"yummy-yummy\""))
.toFileAssert()
// internal xml-array element name (4th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("colors").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("colors").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"color\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"colors\""))
.toProperty().toType()
.assertMethod("getColors").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"color\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"colors\""))
.toMethod().toFileAssert()
.assertMethod("getColors")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"color\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"colors\""))
.toFileAssert()
// ignored external xml-array element name, non-wrapped (2nd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("categories").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("categories").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Category\""))
.toProperty().toType()
.assertMethod("getCategories").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Category\""))
.assertMethod("getCategories")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"Category\""))
// specific regression test for #2417: (useWrapping=false) needs to be present
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toMethod().toFileAssert()
.hasAnnotation("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toFileAssert()
// test custom-name on wrapper AND children (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
// maps to 5th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("activities").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("activities").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"item\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"activities-array\""))
.toProperty().toType()
.assertMethod("getActivities").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"item\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"activities-array\""));
.assertMethod("getActivities")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"item\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"activities-array\""));
}
/**
@ -2845,99 +2832,94 @@ public class JavaClientCodegenTest {
@Test(dataProvider = "librariesNotSupportingJackson")
void shouldGenerateCorrectJaxbAnnotations(Library library) {
// Arrange
final String TEST_SPEC = "src/test/resources/3_0/java/xml-annotations-test.yaml";
final Path output = newTempFolder();
JavaClientCodegen codegen = new JavaClientCodegen();
codegen.setLibrary(library.getValue());
codegen.setSerializationLibrary("jackson");
codegen.setWithXml(true);
codegen.setOutputDir(output.toString());
DefaultGenerator generator = new DefaultGenerator();
generator.setGeneratorPropertyDefault(CodegenConstants.MODELS, "true");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_TESTS, "false");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_DOCS, "false");
generator.setGenerateMetadata(false);
final CodegenConfigurator config = new CodegenConfigurator()
.addAdditionalProperty(CodegenConstants.WITH_XML, true)
.addGlobalProperty(CodegenConstants.MODELS, "Pet")
.addGlobalProperty(CodegenConstants.MODEL_DOCS, null)
.addGlobalProperty(CodegenConstants.MODEL_TESTS, null)
.setGeneratorName("java")
.setLibrary(library.value)
.setInputSpec("src/test/resources/3_0/java/xml-annotations-test.yaml")
.setOutputDir(newTempFolder().toString());
// Act
generator.opts(new ClientOptInput().config(codegen).openAPI(TestUtils.parseSpec(TEST_SPEC))).generate();
final List<File> files = new DefaultGenerator().opts(config.toClientOptInput()).generate();
// Assert
JavaFileAssert.assertThat(output.resolve("src/main/java/org/openapitools/client/model/Pet.java").toFile())
JavaFileAssert.assertThat(files.get(0))
.assertTypeAnnotations()
.containsWithNameAndAttributes("XmlRootElement", Map.of("name", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
.containsWithNameAndAttributes("XmlAccessorType", Map.of("value", "XmlAccessType.FIELD"))
.toType()
// test custom-name on wrapper element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
.hasProperty("tags").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("tags").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Tag\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"TagList\""))
.toProperty().toType()
// custom internal xml-array element name, non-wrapped (1st example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("friends").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("friends").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"friend-pet\""))
.toProperty().toType()
// test custom element name (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Change%20Element%20Names)
.hasProperty("status").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("status").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"PetStatus\""))
.toProperty().toType()
// test same-name wrapping element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Wrapping%20Arrays)
// maps to 3rd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"photoUrls\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"photoUrls\""))
.toProperty().toType()
// test attribute generation (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Convert%20Property%20to%20an%20Attribute)
.hasProperty("name").assertPropertyAnnotations()
.doesNotContainsWithName("XmlElement")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("name").assertPropertyAnnotations()
.doesNotContainWithName("XmlElement")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlAttribute", Map.of("name", "\"name\""))
.toProperty().toType()
// test XML namespace and prefix (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Prefixes%20and%20Namespaces)
.hasProperty("id").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("id").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toProperty().toType()
// external xml-array element name only (last example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("foods").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("foods").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"yummy-yummy\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"yummy-yummy\""))
.toProperty().toType()
// internal xml-array element name (4th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("colors").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("colors").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"color\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"colors\""))
.toProperty().toType()
// ignored external xml-array element name, non-wrapped (2nd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("categories").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("categories").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Category\""))
.toProperty().toType()
// test custom-name on wrapper AND children (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
// maps to 5th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("activities").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("activities").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"item\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"activities-array\""));
}

View File

@ -39,73 +39,73 @@ public class JavaValidationArrayPrimitivesTest {
private static Consumer<Map<String, File>> assertWithValidationWithoutJsonNullable() {
return files -> JavaFileAssert.assertThat(files.get("Foo.java"))
.isNormalClass()
.hasProperty("stringPattern")
.assertProperty("stringPattern")
.withType("Set<@Pattern(regexp = \"[a-z]\") String>")
.toType()
.hasProperty("stringMaxMinLength")
.assertProperty("stringMaxMinLength")
.withType("Set<@Size(min = 1, max = 10) String>")
.toType()
.hasProperty("stringMinLength")
.assertProperty("stringMinLength")
.withType("List<@Size(min = 1) String>")
.toType()
.hasProperty("stringMaxLength")
.assertProperty("stringMaxLength")
.withType("Set<@Size(max = 1) String>")
.toType()
.hasProperty("stringEmail")
.assertProperty("stringEmail")
.withType("List<@Email String>")
.toType()
.hasProperty("intMinMax")
.assertProperty("intMinMax")
.withType("List<@Min(1) @Max(10) Integer>")
.toType()
.hasProperty("intMin")
.assertProperty("intMin")
.withType("List<@Min(1) Integer>")
.toType()
.hasProperty("intMax")
.assertProperty("intMax")
.withType("List<@Max(10) Integer>")
.toType()
.hasProperty("numberMinMax")
.assertProperty("numberMinMax")
.withType("List<@DecimalMin(value = \"1\", inclusive = true) @DecimalMax(value = \"10\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("numberMin")
.assertProperty("numberMin")
.withType("List<@DecimalMin(value = \"1\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("numberMax")
.assertProperty("numberMax")
.withType("List<@DecimalMax(value = \"10\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("stringPatternWithMin")
.assertProperty("stringPatternWithMin")
.withType("Set<@Pattern(regexp = \"^\\\\d{3}-\\\\d{2}-\\\\d{4}$\") @Size(min = 10) String>")
.toType()
.hasProperty("stringPatternNullable")
.assertProperty("stringPatternNullable")
.withType("Set<@Pattern(regexp = \"^\\\\d{3}-\\\\d{2}-\\\\d{4}$\") String>")
.toType()
.hasProperty("stringMaxMinLengthNullable")
.assertProperty("stringMaxMinLengthNullable")
.withType("Set<@Size(min = 1, max = 10) String>")
.toType()
.hasProperty("stringMinLengthNullable")
.assertProperty("stringMinLengthNullable")
.withType("List<@Size(min = 1) String>")
.toType()
.hasProperty("stringMaxLengthNullable")
.assertProperty("stringMaxLengthNullable")
.withType("Set<@Size(max = 1) String>")
.toType()
.hasProperty("stringNumbers")
.assertProperty("stringNumbers")
.withType("Set<@DecimalMin(value = \"1\", inclusive = true) @DecimalMax(value = \"10\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("intMinMaxNullable")
.assertProperty("intMinMaxNullable")
.withType("List<@Min(1) @Max(10) Integer>")
.toType()
.hasProperty("intMinNullable")
.assertProperty("intMinNullable")
.withType("List<@Min(1) Integer>")
.toType()
.hasProperty("intMaxNullable")
.assertProperty("intMaxNullable")
.withType("List<@Max(10) Integer>")
.toType()
.hasProperty("numberMinMaxNullable")
.assertProperty("numberMinMaxNullable")
.withType("List<@DecimalMin(value = \"1\", inclusive = true) @DecimalMax(value = \"10\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("numberMinNullable")
.assertProperty("numberMinNullable")
.withType("List<@DecimalMin(value = \"1\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("numberMaxNullable")
.assertProperty("numberMaxNullable")
.withType("List<@DecimalMax(value = \"10\", inclusive = false) BigDecimal>")
.toType();
}
@ -113,76 +113,76 @@ public class JavaValidationArrayPrimitivesTest {
private static Consumer<Map<String, File>> assertWithValidationWithJsonNullable() {
return files -> JavaFileAssert.assertThat(files.get("Foo.java"))
.isNormalClass()
.hasProperty("category")
.assertProperty("category")
.withType("List<@Pattern(regexp = \"^[a-zA-Z0-9 .:!()-]$\") @Size(max = 50) String>")
.toType()
.hasProperty("stringPattern")
.assertProperty("stringPattern")
.withType("Set<@Pattern(regexp = \"[a-z]\") String>")
.toType()
.hasProperty("stringMaxMinLength")
.assertProperty("stringMaxMinLength")
.withType("Set<@Size(min = 1, max = 10) String>")
.toType()
.hasProperty("stringMinLength")
.assertProperty("stringMinLength")
.withType("List<@Size(min = 1) String>")
.toType()
.hasProperty("stringMaxLength")
.assertProperty("stringMaxLength")
.withType("Set<@Size(max = 1) String>")
.toType()
.hasProperty("stringEmail")
.assertProperty("stringEmail")
.withType("List<@Email String>")
.toType()
.hasProperty("intMinMax")
.assertProperty("intMinMax")
.withType("List<@Min(1) @Max(10) Integer>")
.toType()
.hasProperty("intMin")
.assertProperty("intMin")
.withType("List<@Min(1) Integer>")
.toType()
.hasProperty("intMax")
.assertProperty("intMax")
.withType("List<@Max(10) Integer>")
.toType()
.hasProperty("numberMinMax")
.assertProperty("numberMinMax")
.withType("List<@DecimalMin(value = \"1\", inclusive = true) @DecimalMax(value = \"10\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("numberMin")
.assertProperty("numberMin")
.withType("List<@DecimalMin(value = \"1\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("numberMax")
.assertProperty("numberMax")
.withType("List<@DecimalMax(value = \"10\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("stringPatternWithMin")
.assertProperty("stringPatternWithMin")
.withType("JsonNullable<Set<@Pattern(regexp = \"^\\\\d{3}-\\\\d{2}-\\\\d{4}$\") @Size(min = 10) String>>")
.toType()
.hasProperty("stringPatternNullable")
.assertProperty("stringPatternNullable")
.withType("JsonNullable<Set<@Pattern(regexp = \"^\\\\d{3}-\\\\d{2}-\\\\d{4}$\") String>>")
.toType()
.hasProperty("stringMaxMinLengthNullable")
.assertProperty("stringMaxMinLengthNullable")
.withType("JsonNullable<Set<@Size(min = 1, max = 10) String>>")
.toType()
.hasProperty("stringMinLengthNullable")
.assertProperty("stringMinLengthNullable")
.withType("JsonNullable<List<@Size(min = 1) String>>")
.toType()
.hasProperty("stringMaxLengthNullable")
.assertProperty("stringMaxLengthNullable")
.withType("JsonNullable<Set<@Size(max = 1) String>>")
.toType()
.hasProperty("stringNumbers")
.assertProperty("stringNumbers")
.withType("Set<@DecimalMin(value = \"1\", inclusive = true) @DecimalMax(value = \"10\", inclusive = true) BigDecimal>")
.toType()
.hasProperty("intMinMaxNullable")
.assertProperty("intMinMaxNullable")
.withType("JsonNullable<List<@Min(1) @Max(10) Integer>>")
.toType()
.hasProperty("intMinNullable")
.assertProperty("intMinNullable")
.withType("JsonNullable<List<@Min(1) Integer>>")
.toType()
.hasProperty("intMaxNullable")
.assertProperty("intMaxNullable")
.withType("JsonNullable<List<@Max(10) Integer>>")
.toType()
.hasProperty("numberMinMaxNullable")
.assertProperty("numberMinMaxNullable")
.withType("JsonNullable<List<@DecimalMin(value = \"1\", inclusive = true) @DecimalMax(value = \"10\", inclusive = true) BigDecimal>>")
.toType()
.hasProperty("numberMinNullable")
.assertProperty("numberMinNullable")
.withType("JsonNullable<List<@DecimalMin(value = \"1\", inclusive = true) BigDecimal>>")
.toType()
.hasProperty("numberMaxNullable")
.assertProperty("numberMaxNullable")
.withType("JsonNullable<List<@DecimalMax(value = \"10\", inclusive = false) BigDecimal>>")
.toType();
}
@ -231,70 +231,70 @@ public class JavaValidationArrayPrimitivesTest {
private static Consumer<Map<String, File>> assertWithoutValidationWithoutJsonNullable() {
return files -> JavaFileAssert.assertThat(files.get("Foo.java"))
.isNormalClass()
.hasProperty("stringPattern")
.assertProperty("stringPattern")
.withType("Set<String>")
.toType()
.hasProperty("stringMaxMinLength")
.assertProperty("stringMaxMinLength")
.withType("Set<String>")
.toType()
.hasProperty("stringMinLength")
.assertProperty("stringMinLength")
.withType("List<String>")
.toType()
.hasProperty("stringMaxLength")
.assertProperty("stringMaxLength")
.withType("Set<String>")
.toType()
.hasProperty("stringEmail")
.assertProperty("stringEmail")
.withType("List<String>")
.toType()
.hasProperty("intMinMax")
.assertProperty("intMinMax")
.withType("List<Integer>")
.toType()
.hasProperty("intMin")
.assertProperty("intMin")
.withType("List<Integer>")
.toType()
.hasProperty("intMax")
.assertProperty("intMax")
.withType("List<Integer>")
.toType()
.hasProperty("numberMinMax")
.assertProperty("numberMinMax")
.withType("List<BigDecimal>")
.toType()
.hasProperty("numberMin")
.assertProperty("numberMin")
.withType("List<BigDecimal>")
.toType()
.hasProperty("numberMax")
.assertProperty("numberMax")
.withType("List<BigDecimal>")
.toType()
.hasProperty("stringPatternWithMin")
.assertProperty("stringPatternWithMin")
.withType("Set<String>")
.toType()
.hasProperty("stringPatternNullable")
.assertProperty("stringPatternNullable")
.withType("Set<String>")
.toType()
.hasProperty("stringMaxMinLengthNullable")
.assertProperty("stringMaxMinLengthNullable")
.withType("Set<String>")
.toType()
.hasProperty("stringMinLengthNullable")
.assertProperty("stringMinLengthNullable")
.withType("List<String>")
.toType()
.hasProperty("stringMaxLengthNullable")
.assertProperty("stringMaxLengthNullable")
.withType("Set<String>")
.toType()
.hasProperty("intMinMaxNullable")
.assertProperty("intMinMaxNullable")
.withType("List<Integer>")
.toType()
.hasProperty("intMinNullable")
.assertProperty("intMinNullable")
.withType("List<Integer>")
.toType()
.hasProperty("intMaxNullable")
.assertProperty("intMaxNullable")
.withType("List<Integer>")
.toType()
.hasProperty("numberMinMaxNullable")
.assertProperty("numberMinMaxNullable")
.withType("List<BigDecimal>")
.toType()
.hasProperty("numberMinNullable")
.assertProperty("numberMinNullable")
.withType("List<BigDecimal>")
.toType()
.hasProperty("numberMaxNullable")
.assertProperty("numberMaxNullable")
.withType("List<BigDecimal>")
.toType();
}
@ -302,70 +302,70 @@ public class JavaValidationArrayPrimitivesTest {
private static Consumer<Map<String, File>> assertWithoutValidationWithJsonNullable() {
return files -> JavaFileAssert.assertThat(files.get("Foo.java"))
.isNormalClass()
.hasProperty("stringPattern")
.assertProperty("stringPattern")
.withType("Set<String>")
.toType()
.hasProperty("stringMaxMinLength")
.assertProperty("stringMaxMinLength")
.withType("Set<String>")
.toType()
.hasProperty("stringMinLength")
.assertProperty("stringMinLength")
.withType("List<String>")
.toType()
.hasProperty("stringMaxLength")
.assertProperty("stringMaxLength")
.withType("Set<String>")
.toType()
.hasProperty("stringEmail")
.assertProperty("stringEmail")
.withType("List<String>")
.toType()
.hasProperty("intMinMax")
.assertProperty("intMinMax")
.withType("List<Integer>")
.toType()
.hasProperty("intMin")
.assertProperty("intMin")
.withType("List<Integer>")
.toType()
.hasProperty("intMax")
.assertProperty("intMax")
.withType("List<Integer>")
.toType()
.hasProperty("numberMinMax")
.assertProperty("numberMinMax")
.withType("List<BigDecimal>")
.toType()
.hasProperty("numberMin")
.assertProperty("numberMin")
.withType("List<BigDecimal>")
.toType()
.hasProperty("numberMax")
.assertProperty("numberMax")
.withType("List<BigDecimal>")
.toType()
.hasProperty("stringPatternWithMin")
.assertProperty("stringPatternWithMin")
.withType("JsonNullable<Set<String>>")
.toType()
.hasProperty("stringPatternNullable")
.assertProperty("stringPatternNullable")
.withType("JsonNullable<Set<String>>")
.toType()
.hasProperty("stringMaxMinLengthNullable")
.assertProperty("stringMaxMinLengthNullable")
.withType("JsonNullable<Set<String>>")
.toType()
.hasProperty("stringMinLengthNullable")
.assertProperty("stringMinLengthNullable")
.withType("JsonNullable<List<String>>")
.toType()
.hasProperty("stringMaxLengthNullable")
.assertProperty("stringMaxLengthNullable")
.withType("JsonNullable<Set<String>>")
.toType()
.hasProperty("intMinMaxNullable")
.assertProperty("intMinMaxNullable")
.withType("JsonNullable<List<Integer>>")
.toType()
.hasProperty("intMinNullable")
.assertProperty("intMinNullable")
.withType("JsonNullable<List<Integer>>")
.toType()
.hasProperty("intMaxNullable")
.assertProperty("intMaxNullable")
.withType("JsonNullable<List<Integer>>")
.toType()
.hasProperty("numberMinMaxNullable")
.assertProperty("numberMinMaxNullable")
.withType("JsonNullable<List<BigDecimal>>")
.toType()
.hasProperty("numberMinNullable")
.assertProperty("numberMinNullable")
.withType("JsonNullable<List<BigDecimal>>")
.toType()
.hasProperty("numberMaxNullable")
.assertProperty("numberMaxNullable")
.withType("JsonNullable<List<BigDecimal>>")
.toType();
}

View File

@ -17,9 +17,9 @@ import com.github.javaparser.ast.nodeTypes.NodeWithSimpleName;
import com.google.common.collect.ImmutableMap;
@CanIgnoreReturnValue
public abstract class AbstractAnnotationAssert<ACTUAL extends AbstractAnnotationAssert<ACTUAL>> extends ListAssert<AnnotationExpr> {
public abstract class AbstractAnnotationsAssert<ACTUAL extends AbstractAnnotationsAssert<ACTUAL>> extends ListAssert<AnnotationExpr> {
protected AbstractAnnotationAssert(final List<AnnotationExpr> annotationExpr) {
protected AbstractAnnotationsAssert(final List<AnnotationExpr> annotationExpr) {
super(annotationExpr);
}
@ -36,7 +36,7 @@ public abstract class AbstractAnnotationAssert<ACTUAL extends AbstractAnnotation
return myself();
}
public ACTUAL doesNotContainsWithName(final String name) {
public ACTUAL doesNotContainWithName(final String name) {
super
.withFailMessage("Shouldn't have annotation with name: " + name)
.noneMatch(annotation -> annotation.getNameAsString().equals(name));

View File

@ -0,0 +1,152 @@
package org.openapitools.codegen.java.assertions;
import com.github.javaparser.ast.body.ClassOrInterfaceDeclaration;
import com.github.javaparser.ast.body.MethodDeclaration;
import com.github.javaparser.ast.nodeTypes.NodeWithName;
import org.assertj.core.api.AbstractAssert;
import org.assertj.core.api.Assertions;
import org.assertj.core.util.CanIgnoreReturnValue;
import java.util.Arrays;
import java.util.Map;
import java.util.stream.Collectors;
@CanIgnoreReturnValue
public abstract class AbstractMethodAssert<ACTUAL extends AbstractMethodAssert<ACTUAL>> extends AbstractAssert<AbstractMethodAssert<ACTUAL>, MethodDeclaration> {
protected final String methodSignature;
protected AbstractMethodAssert(MethodDeclaration methodDeclaration, Class<?> selfType) {
super(methodDeclaration, selfType);
this.methodSignature = methodDeclaration.getDeclarationAsString();
}
public abstract JavaFileAssert toFileAssert();
public abstract AbstractAnnotationsAssert<?> assertMethodAnnotations();
public ACTUAL hasReturnType(final String returnType) {
Assertions.assertThat(actual.getType().toString())
.isEqualTo(returnType);
return myself();
}
public ACTUAL hasAnnotation(String annotation) {
assertMethodAnnotations().containsWithName(annotation);
return myself();
}
public ACTUAL hasAnnotation(String annotation, final Map<String, String> attributes) {
assertMethodAnnotations().containsWithNameAndAttributes(annotation, attributes);
return myself();
}
public ACTUAL doesNotHaveAnnotation(String annotation) {
assertMethodAnnotations().doesNotContainWithName(annotation);
return myself();
}
public ACTUAL doesNotHaveParameter(final String paramName) {
Assertions.assertThat(actual.getParameterByName(paramName))
.withFailMessage("Method %s shouldn't have parameter %s, but it does", methodSignature, paramName)
.isEmpty();
return myself();
}
public ACTUAL doesNotHaveParameters() {
Assertions.assertThat(actual.getParameters())
.withFailMessage("Method %s shouldn't have parameter, but it does", methodSignature)
.isEmpty();
return myself();
}
public ACTUAL bodyContainsLines(final String... lines) {
Assertions.assertThat(isWithImplementation())
.withFailMessage("Method %s is abstract", methodSignature)
.isTrue();
final String actualBody = actual.getTokenRange()
.orElseThrow(() -> new IllegalStateException("Not-abstract method doesn't have body"))
.toString();
Assertions.assertThat(actualBody)
.withFailMessage(
"Method's %s body should contains lines\n====\n%s\n====\nbut actually was\n====\n%s\n====",
methodSignature, Arrays.stream(lines).collect(Collectors.joining(System.lineSeparator())), actualBody
)
.contains(lines);
return myself();
}
public ACTUAL bodyNotContainsLines(final String... lines) {
Assertions.assertThat(isWithImplementation())
.withFailMessage("Method %s is abstract", methodSignature)
.isTrue();
final String actualBody = actual.getTokenRange()
.orElseThrow(() -> new IllegalStateException("Not-abstract method doesn't have body"))
.toString();
Assertions.assertThat(actualBody)
.withFailMessage(
"Method's %s body shouldn't contains lines\n====\n%s\n====\nbut actually was\n====\n%s\n====",
methodSignature, Arrays.stream(lines).collect(Collectors.joining(System.lineSeparator())), actualBody
)
.doesNotContain(lines);
return myself();
}
public ACTUAL doesNotHaveImplementation() {
Assertions.assertThat(isWithImplementation())
.withFailMessage("Method %s should be abstract", methodSignature)
.isFalse();
return myself();
}
public ACTUAL doesNotHaveComment() {
Assertions.assertThat(actual.getJavadocComment())
.withFailMessage("Method %s shouldn't contains comment, but it does", methodSignature)
.isEmpty();
return myself();
}
@SuppressWarnings("OptionalGetWithoutIsPresent")
public ACTUAL commentContainsLines(final String... lines) {
Assertions.assertThat(actual.getJavadocComment())
.withFailMessage("Method %s should contains comment, but it doesn't", methodSignature)
.isPresent();
final String actualComment = actual.getJavadocComment().get().getContent();
Assertions.assertThat(actualComment)
.withFailMessage(
"Method's %s comment should contains lines\n====\n%s\n====\nbut actually was\n====%s\n====",
methodSignature, Arrays.stream(lines).collect(Collectors.joining(System.lineSeparator())), actualComment
)
.contains(lines);
return myself();
}
public ACTUAL noneOfParameterHasAnnotation(final String annotationName) {
actual.getParameters()
.forEach(
param -> Assertions.assertThat(param.getAnnotations())
.withFailMessage("Parameter %s contains annotation %s while it shouldn't", param.getNameAsString(), annotationName)
.extracting(NodeWithName::getNameAsString)
.doesNotContain(annotationName)
);
return myself();
}
private boolean isWithImplementation() {
final boolean isInterface = actual.getParentNode()
.filter(ClassOrInterfaceDeclaration.class::isInstance)
.map(ClassOrInterfaceDeclaration.class::cast)
.map(ClassOrInterfaceDeclaration::isInterface)
.orElse(false);
return !(actual.isAbstract() || (isInterface && !actual.isDefault()));
}
@SuppressWarnings("unchecked")
private ACTUAL myself() {
return (ACTUAL) this;
}
}

View File

@ -27,10 +27,11 @@ public class ConstructorAssert extends AbstractAssert<ConstructorAssert, Constru
return fileAssert;
}
public MethodAnnotationAssert assertConstructorAnnotations() {
return new MethodAnnotationAssert(this, actual.getAnnotations());
public MethodAnnotationsAssert assertConstructorAnnotations() {
return new MethodAnnotationsAssert(this, actual.getAnnotations());
}
@SuppressWarnings("OptionalGetWithoutIsPresent")
public ParameterAssert hasParameter(final String paramName) {
final Optional<Parameter> parameter = actual.getParameterByName(paramName);
Assertions.assertThat(parameter)
@ -67,6 +68,7 @@ public class ConstructorAssert extends AbstractAssert<ConstructorAssert, Constru
return this;
}
@SuppressWarnings("OptionalGetWithoutIsPresent")
public ConstructorAssert commentContainsLines(final String... lines) {
Assertions.assertThat(actual.getJavadocComment())
.withFailMessage("Constructor %s should contains comment, but it doesn't", signature)

View File

@ -0,0 +1,87 @@
package org.openapitools.codegen.java.assertions;
import com.github.javaparser.ast.body.ClassOrInterfaceDeclaration;
import com.github.javaparser.ast.body.MethodDeclaration;
import com.github.javaparser.ast.expr.AnnotationExpr;
import org.assertj.core.api.AbstractAssert;
import org.assertj.core.api.Assertions;
import java.util.Arrays;
import java.util.List;
public class InnerClassAssert extends AbstractAssert<InnerClassAssert, ClassOrInterfaceDeclaration> {
private final JavaFileAssert parent;
private final ClassOrInterfaceDeclaration innerClass;
protected InnerClassAssert(final JavaFileAssert fileAssert, final ClassOrInterfaceDeclaration bodyDeclaration) {
super(bodyDeclaration, InnerClassAssert.class);
parent = fileAssert;
innerClass = bodyDeclaration;
}
public JavaFileAssert toFileAssert() {
return parent;
}
// TODO this effectively duplicates JavaFileAssert.assertMethod, could be moved into a common
// intermediate base class (which would then easily implement property, type & constructor
// assertions for inner classes
public MethodAssert assertMethod(final String methodName, final String... paramTypes) {
final List<MethodDeclaration> methods = paramTypes.length == 0
? innerClass.getMethodsByName(methodName)
: innerClass.getMethodsBySignature(methodName, paramTypes);
final String failMessage = (methods.isEmpty()
? "No methods matching `%s(%s)` exist"
: "There are " + methods.size() + " methods matching `%s(%s)`")
+ " in inner class `" + innerClass.getName() + "`";
Assertions.assertThat(methods)
.withFailMessage(failMessage, methodName, Arrays.toString(paramTypes).replaceAll("\\[]", ""))
.hasSize(1);
return new MethodAssert(this, methods.get(0));
}
public static class MethodAssert extends AbstractMethodAssert<MethodAssert> {
private final InnerClassAssert innerClassAssert;
MethodAssert(InnerClassAssert innerClassAssert, MethodDeclaration methodDeclaration) {
super(methodDeclaration, MethodAssert.class);
this.innerClassAssert = innerClassAssert;
}
public MethodAnnotationsAssert assertMethodAnnotations() {
return new MethodAnnotationsAssert(this, actual.getAnnotations());
}
public InnerClassAssert toInnerClassAssert() {
return innerClassAssert;
}
public JavaFileAssert toFileAssert() {
return innerClassAssert.toFileAssert();
}
}
public static class MethodAnnotationsAssert extends AbstractAnnotationsAssert<MethodAnnotationsAssert> {
private final MethodAssert parent;
protected MethodAnnotationsAssert(MethodAssert methodAssert, List<AnnotationExpr> annotationExpr) {
super(annotationExpr);
parent = methodAssert;
}
public InnerClassAssert toInnerClassAssert() {
return parent.innerClassAssert;
}
public MethodAssert toMethod() {
return parent;
}
}
}

View File

@ -1,5 +1,14 @@
package org.openapitools.codegen.java.assertions;
import com.github.javaparser.StaticJavaParser;
import com.github.javaparser.ast.CompilationUnit;
import com.github.javaparser.ast.body.*;
import com.github.javaparser.ast.nodeTypes.NodeWithName;
import com.github.javaparser.ast.nodeTypes.modifiers.NodeWithAbstractModifier;
import org.assertj.core.api.AbstractAssert;
import org.assertj.core.api.Assertions;
import org.assertj.core.util.CanIgnoreReturnValue;
import java.io.File;
import java.io.IOException;
import java.nio.file.Path;
@ -8,19 +17,6 @@ import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;
import com.github.javaparser.ast.body.ClassOrInterfaceDeclaration;
import com.github.javaparser.ast.body.ConstructorDeclaration;
import org.assertj.core.api.AbstractAssert;
import org.assertj.core.api.Assertions;
import org.assertj.core.util.CanIgnoreReturnValue;
import com.github.javaparser.StaticJavaParser;
import com.github.javaparser.ast.CompilationUnit;
import com.github.javaparser.ast.body.FieldDeclaration;
import com.github.javaparser.ast.body.MethodDeclaration;
import com.github.javaparser.ast.nodeTypes.NodeWithName;
import com.github.javaparser.ast.nodeTypes.modifiers.NodeWithAbstractModifier;
@CanIgnoreReturnValue
public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUnit> {
@ -41,11 +37,7 @@ public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUn
}
public static JavaFileAssert assertThat(final File file) {
try {
return new JavaFileAssert(StaticJavaParser.parse(file));
} catch (IOException e) {
throw new RuntimeException("Exception while reading file: " + file, e);
}
return assertThat(file.toPath());
}
public JavaFileAssert isInterface() {
@ -72,7 +64,7 @@ public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUn
return this;
}
public JavaFileAssert assertNoMethod(final String methodName, final String... paramTypes) {
public JavaFileAssert hasNoMethod(final String methodName, final String... paramTypes) {
List<MethodDeclaration> methods = paramTypes.length == 0
? actual.getType(0).getMethodsByName(methodName)
: actual.getType(0).getMethodsBySignature(methodName, paramTypes);
@ -98,7 +90,23 @@ public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUn
return new MethodAssert(this, methods.get(0));
}
@SuppressWarnings("OptionalGetWithoutIsPresent")
public InnerClassAssert assertInnerClass(final String className) {
Optional<ClassOrInterfaceDeclaration> innerClass = actual.getType(0).getMembers().stream()
.filter(BodyDeclaration::isClassOrInterfaceDeclaration)
.map(clazz -> (ClassOrInterfaceDeclaration) clazz)
.filter(clazz -> clazz.isInnerClass() || clazz.isStatic() && clazz.getNameAsString().equals(className))
.findFirst();
Assertions.assertThat(innerClass)
.withFailMessage("No inner class with name %s found", className)
.isPresent();
return new InnerClassAssert(this, innerClass.get ());
}
@SuppressWarnings("OptionalGetWithoutIsPresent")
public ConstructorAssert assertConstructor(final String... paramTypes) {
Optional<ConstructorDeclaration> constructorDeclaration = actual.getType(0).getConstructorByParameterTypes(paramTypes);
Assertions.assertThat(constructorDeclaration)
@ -108,7 +116,7 @@ public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUn
return new ConstructorAssert(this, constructorDeclaration.get());
}
public JavaFileAssert assertNoConstructor(final String... paramTypes) {
public JavaFileAssert hasNoConstructor(final String... paramTypes) {
Optional<ConstructorDeclaration> constructorDeclaration = actual.getType(0).getConstructorByParameterTypes(paramTypes);
Assertions.assertThat(constructorDeclaration)
.withFailMessage("Found constructor with parameter(s) %s", Arrays.toString(paramTypes))
@ -117,7 +125,8 @@ public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUn
return this;
}
public PropertyAssert hasProperty(final String propertyName) {
@SuppressWarnings("OptionalGetWithoutIsPresent")
public PropertyAssert assertProperty(final String propertyName) {
Optional<FieldDeclaration> fieldOptional = actual.getType(0).getMembers().stream()
.filter(FieldDeclaration.class::isInstance)
.map(FieldDeclaration.class::cast)
@ -161,7 +170,7 @@ public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUn
return this;
}
public JavaFileAssert fileDoesNotContains(final String... lines) {
public JavaFileAssert fileDoesNotContain(final String... lines) {
final String actualBody = actual.getTokenRange()
.orElseThrow(() -> new IllegalStateException("Empty file"))
.toString();
@ -175,8 +184,7 @@ public class JavaFileAssert extends AbstractAssert<JavaFileAssert, CompilationUn
return this;
}
public TypeAnnotationAssert assertTypeAnnotations() {
return new TypeAnnotationAssert(this, actual.getType(0).getAnnotations());
public TypeAnnotationsAssert assertTypeAnnotations() {
return new TypeAnnotationsAssert(this, actual.getType(0).getAnnotations());
}
}

View File

@ -7,18 +7,18 @@ import org.assertj.core.util.CanIgnoreReturnValue;
import com.github.javaparser.ast.expr.AnnotationExpr;
@CanIgnoreReturnValue
public class MethodAnnotationAssert extends AbstractAnnotationAssert<MethodAnnotationAssert> {
public class MethodAnnotationsAssert extends AbstractAnnotationsAssert<MethodAnnotationsAssert> {
private final MethodAssert methodAssert;
private final ConstructorAssert constructorAssert;
protected MethodAnnotationAssert(final MethodAssert methodAssert, final List<AnnotationExpr> annotationExpr) {
protected MethodAnnotationsAssert(final MethodAssert methodAssert, final List<AnnotationExpr> annotationExpr) {
super(annotationExpr);
this.methodAssert = methodAssert;
this.constructorAssert = null;
}
protected MethodAnnotationAssert(final ConstructorAssert constructorAssert, final List<AnnotationExpr> annotationExpr) {
protected MethodAnnotationsAssert(final ConstructorAssert constructorAssert, final List<AnnotationExpr> annotationExpr) {
super(annotationExpr);
this.constructorAssert = constructorAssert;
this.methodAssert = null;

View File

@ -1,148 +1,38 @@
package org.openapitools.codegen.java.assertions;
import java.util.Arrays;
import java.util.Optional;
import java.util.stream.Collectors;
import org.assertj.core.api.AbstractAssert;
import org.assertj.core.api.Assertions;
import org.assertj.core.util.CanIgnoreReturnValue;
import com.github.javaparser.ast.body.ClassOrInterfaceDeclaration;
import com.github.javaparser.ast.body.MethodDeclaration;
import com.github.javaparser.ast.body.Parameter;
import com.github.javaparser.ast.nodeTypes.NodeWithName;
import org.assertj.core.api.Assertions;
@CanIgnoreReturnValue
public class MethodAssert extends AbstractAssert<MethodAssert, MethodDeclaration> {
import java.util.Optional;
public class MethodAssert extends AbstractMethodAssert<MethodAssert> {
private final JavaFileAssert fileAssert;
private final String methodSignature;
MethodAssert(final JavaFileAssert fileAssert, final MethodDeclaration methodDeclaration) {
super(methodDeclaration, MethodAssert.class);
this.fileAssert = fileAssert;
this.methodSignature = methodDeclaration.getDeclarationAsString();
}
public JavaFileAssert toFileAssert() {
return fileAssert;
}
public MethodAnnotationAssert assertMethodAnnotations() {
return new MethodAnnotationAssert(this, actual.getAnnotations());
public MethodAnnotationsAssert assertMethodAnnotations() {
return new MethodAnnotationsAssert(this, actual.getAnnotations());
}
public MethodAssert hasReturnType(final String returnType) {
Assertions.assertThat(actual.getType().toString())
.isEqualTo(returnType);
return this;
}
public ParameterAssert hasParameter(final String paramName) {
// TODO move into base class so inner class method parameters can be asserted
// (may need some more Generics Kung-Fu applied to the ParameterAssert class,
// alternatively the f)
@SuppressWarnings("OptionalGetWithoutIsPresent")
public ParameterAssert assertParameter(final String paramName) {
final Optional<Parameter> parameter = actual.getParameterByName(paramName);
Assertions.assertThat(parameter)
.withFailMessage("Method %s should have parameter %s, but it doesn't", methodSignature, paramName)
.isPresent();
return new ParameterAssert(this, parameter.get());
}
public MethodAssert doesNotHaveParameter(final String paramName) {
Assertions.assertThat(actual.getParameterByName(paramName))
.withFailMessage("Method %s shouldn't have parameter %s, but it does", methodSignature, paramName)
.isEmpty();
return this;
}
public MethodAssert doesNotHaveParameters() {
Assertions.assertThat(actual.getParameters())
.withFailMessage("Method %s shouldn't have parameter, but it does", methodSignature)
.isEmpty();
return this;
}
public MethodAssert bodyContainsLines(final String... lines) {
Assertions.assertThat(isWithImplementation())
.withFailMessage("Method %s is abstract", methodSignature)
.isTrue();
final String actualBody = actual.getTokenRange()
.orElseThrow(() -> new IllegalStateException("Not-abstract method doesn't have body"))
.toString();
Assertions.assertThat(actualBody)
.withFailMessage(
"Method's %s body should contains lines\n====\n%s\n====\nbut actually was\n====\n%s\n====",
methodSignature, Arrays.stream(lines).collect(Collectors.joining(System.lineSeparator())), actualBody
)
.contains(lines);
return this;
}
public MethodAssert bodyNotContainsLines(final String... lines) {
Assertions.assertThat(isWithImplementation())
.withFailMessage("Method %s is abstract", methodSignature)
.isTrue();
final String actualBody = actual.getTokenRange()
.orElseThrow(() -> new IllegalStateException("Not-abstract method doesn't have body"))
.toString();
Assertions.assertThat(actualBody)
.withFailMessage(
"Method's %s body shouldn't contains lines\n====\n%s\n====\nbut actually was\n====\n%s\n====",
methodSignature, Arrays.stream(lines).collect(Collectors.joining(System.lineSeparator())), actualBody
)
.doesNotContain(lines);
return this;
}
public MethodAssert doesNotHaveImplementation() {
Assertions.assertThat(isWithImplementation())
.withFailMessage("Method %s should be abstract", methodSignature)
.isFalse();
return this;
}
public MethodAssert doesNotHaveComment() {
Assertions.assertThat(actual.getJavadocComment())
.withFailMessage("Method %s shouldn't contains comment, but it does", methodSignature)
.isEmpty();
return this;
}
public MethodAssert commentContainsLines(final String... lines) {
Assertions.assertThat(actual.getJavadocComment())
.withFailMessage("Method %s should contains comment, but it doesn't", methodSignature)
.isPresent();
final String actualComment = actual.getJavadocComment().get().getContent();
Assertions.assertThat(actualComment)
.withFailMessage(
"Method's %s comment should contains lines\n====\n%s\n====\nbut actually was\n====%s\n====",
methodSignature, Arrays.stream(lines).collect(Collectors.joining(System.lineSeparator())), actualComment
)
.contains(lines);
return this;
}
public MethodAssert noneOfParameterHasAnnotation(final String annotationName) {
actual.getParameters()
.forEach(
param -> Assertions.assertThat(param.getAnnotations())
.withFailMessage("Parameter %s contains annotation %s while it shouldn't", param.getNameAsString(), annotationName)
.extracting(NodeWithName::getNameAsString)
.doesNotContain(annotationName)
);
return this;
}
private boolean isWithImplementation() {
final boolean isInterface = actual.getParentNode()
.filter(ClassOrInterfaceDeclaration.class::isInstance)
.map(ClassOrInterfaceDeclaration.class::cast)
.map(ClassOrInterfaceDeclaration::isInterface)
.orElse(false);
return !(actual.isAbstract() || (isInterface && !actual.isDefault()));
}
}

View File

@ -7,11 +7,11 @@ import org.assertj.core.util.CanIgnoreReturnValue;
import com.github.javaparser.ast.expr.AnnotationExpr;
@CanIgnoreReturnValue
public class ParameterAnnotationAssert extends AbstractAnnotationAssert<ParameterAnnotationAssert> {
public class ParameterAnnotationsAssert extends AbstractAnnotationsAssert<ParameterAnnotationsAssert> {
private final ParameterAssert parameterAssert;
protected ParameterAnnotationAssert(final ParameterAssert parameterAssert, final List<AnnotationExpr> annotationExpr) {
protected ParameterAnnotationsAssert(final ParameterAssert parameterAssert, final List<AnnotationExpr> annotationExpr) {
super(annotationExpr);
this.parameterAssert = parameterAssert;
}

View File

@ -38,14 +38,14 @@ public class ParameterAssert extends ObjectAssert<Parameter> {
return constructorAssert;
}
public ParameterAssert withType(final String expectedType) {
public ParameterAssert hasType(final String expectedType) {
Assertions.assertThat(actual.getTypeAsString())
.withFailMessage("Expected parameter to have type %s, but was %s", expectedType, actual.getTypeAsString())
.isEqualTo(expectedType);
return this;
}
public ParameterAnnotationAssert assertParameterAnnotations() {
return new ParameterAnnotationAssert(this, actual.getAnnotations());
public ParameterAnnotationsAssert assertParameterAnnotations() {
return new ParameterAnnotationsAssert(this, actual.getAnnotations());
}
}

View File

@ -7,11 +7,11 @@ import org.assertj.core.util.CanIgnoreReturnValue;
import com.github.javaparser.ast.expr.AnnotationExpr;
@CanIgnoreReturnValue
public class PropertyAnnotationAssert extends AbstractAnnotationAssert<PropertyAnnotationAssert> {
public class PropertyAnnotationsAssert extends AbstractAnnotationsAssert<PropertyAnnotationsAssert> {
private final PropertyAssert propertyAssert;
protected PropertyAnnotationAssert(final PropertyAssert propertyAssert, final List<AnnotationExpr> annotationExpr) {
protected PropertyAnnotationsAssert(final PropertyAssert propertyAssert, final List<AnnotationExpr> annotationExpr) {
super(annotationExpr);
this.propertyAssert = propertyAssert;
}

View File

@ -27,7 +27,7 @@ public class PropertyAssert extends ObjectAssert<FieldDeclaration> {
return this;
}
public PropertyAnnotationAssert assertPropertyAnnotations() {
return new PropertyAnnotationAssert(this, actual.getAnnotations());
public PropertyAnnotationsAssert assertPropertyAnnotations() {
return new PropertyAnnotationsAssert(this, actual.getAnnotations());
}
}

View File

@ -7,11 +7,11 @@ import org.assertj.core.util.CanIgnoreReturnValue;
import com.github.javaparser.ast.expr.AnnotationExpr;
@CanIgnoreReturnValue
public class TypeAnnotationAssert extends AbstractAnnotationAssert<TypeAnnotationAssert> {
public class TypeAnnotationsAssert extends AbstractAnnotationsAssert<TypeAnnotationsAssert> {
private final JavaFileAssert fileAssert;
protected TypeAnnotationAssert(final JavaFileAssert fileAssert, final List<AnnotationExpr> annotationExpr) {
protected TypeAnnotationsAssert(final JavaFileAssert fileAssert, final List<AnnotationExpr> annotationExpr) {
super(annotationExpr);
this.fileAssert = fileAssert;
}

View File

@ -48,53 +48,53 @@ public class JavaJAXRSCXFCDIServerCodegenTest extends JavaJaxrsBaseTest {
JavaFileAssert.assertThat(files.get("TestHeadersApi.java"))
.assertMethod("headersTest")
.hasParameter("headerNumber").withType("BigDecimal")
.assertParameter("headerNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("headerString").withType("String")
.assertParameter("headerString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringWrapped").withType("String")
.assertParameter("headerStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotes").withType("String")
.assertParameter("headerStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotesWrapped").withType("String")
.assertParameter("headerStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerBoolean").withType("Boolean")
.assertParameter("headerBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"true\""));
JavaFileAssert.assertThat(files.get("TestQueryParamsApi.java"))
.assertMethod("queryParamsTest")
.hasParameter("queryNumber").withType("BigDecimal")
.assertParameter("queryNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("queryString").withType("String")
.assertParameter("queryString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringWrapped").withType("String")
.assertParameter("queryStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotes").withType("String")
.assertParameter("queryStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotesWrapped").withType("String")
.assertParameter("queryStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryBoolean").withType("Boolean")
.assertParameter("queryBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"true\""));
}

View File

@ -293,7 +293,7 @@ public class JavaJAXRSSpecServerCodegenTest extends JavaJaxrsBaseTest {
List<File> files = generator.opts(clientOptInput).generate();
validateJavaSourceFiles(files);
TestUtils.ensureDoesNotContainsFile(files, output, "src/main/openapi/openapi.yaml");
TestUtils.ensureDoesNotContainFile(files, output, "src/main/openapi/openapi.yaml");
output.deleteOnExit();
}
@ -660,53 +660,53 @@ public class JavaJAXRSSpecServerCodegenTest extends JavaJaxrsBaseTest {
JavaFileAssert.assertThat(files.get("TestHeadersApi.java"))
.assertMethod("headersTest")
.hasParameter("headerNumber").withType("BigDecimal")
.assertParameter("headerNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("headerString").withType("String")
.assertParameter("headerString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringWrapped").withType("String")
.assertParameter("headerStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotes").withType("String")
.assertParameter("headerStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotesWrapped").withType("String")
.assertParameter("headerStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerBoolean").withType("Boolean")
.assertParameter("headerBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"true\""));
JavaFileAssert.assertThat(files.get("TestQueryParamsApi.java"))
.assertMethod("queryParamsTest")
.hasParameter("queryNumber").withType("BigDecimal")
.assertParameter("queryNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("queryString").withType("String")
.assertParameter("queryString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringWrapped").withType("String")
.assertParameter("queryStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotes").withType("String")
.assertParameter("queryStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotesWrapped").withType("String")
.assertParameter("queryStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryBoolean").withType("Boolean")
.assertParameter("queryBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"true\""));
}
@ -731,9 +731,9 @@ public class JavaJAXRSSpecServerCodegenTest extends JavaJaxrsBaseTest {
JavaFileAssert.assertThat(files.get("ComplexObject.java"))
.fileContains("private @Valid List<LocalDate> dates")
.fileDoesNotContains("private @Valid SymbolTypeEnum symbolType")
.fileDoesNotContains("@Valid String")
.fileDoesNotContains("@Valid Double");
.fileDoesNotContain("private @Valid SymbolTypeEnum symbolType")
.fileDoesNotContain("@Valid String")
.fileDoesNotContain("@Valid Double");
}
@Test
@ -921,7 +921,7 @@ public class JavaJAXRSSpecServerCodegenTest extends JavaJaxrsBaseTest {
.collect(Collectors.toMap(File::getName, Function.identity()));
JavaFileAssert.assertThat(files.get("ReadonlyAndRequiredProperties.java"))
.hasProperty("requiredYesReadonlyYes")
.assertProperty("requiredYesReadonlyYes")
.toType()
.assertMethod("getRequiredYesReadonlyYes")
.assertMethodAnnotations()
@ -931,7 +931,7 @@ public class JavaJAXRSSpecServerCodegenTest extends JavaJaxrsBaseTest {
.containsWithNameAndAttributes("JsonProperty", ImmutableMap.of("value", "\"requiredYesReadonlyYes\""))
.toMethod()
.toFileAssert()
.hasProperty("requiredYesReadonlyNo")
.assertProperty("requiredYesReadonlyNo")
.toType()
.assertMethod("getRequiredYesReadonlyNo")
.assertMethodAnnotations()

View File

@ -97,53 +97,53 @@ public class JavaJaxrsResteasyServerCodegenModelTest extends JavaJaxrsBaseTest {
JavaFileAssert.assertThat(files.get("TestHeadersApi.java"))
.assertMethod("headersTest")
.hasParameter("headerNumber").withType("BigDecimal")
.assertParameter("headerNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("headerString").withType("String")
.assertParameter("headerString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringWrapped").withType("String")
.assertParameter("headerStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotes").withType("String")
.assertParameter("headerStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotesWrapped").withType("String")
.assertParameter("headerStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerBoolean").withType("Boolean")
.assertParameter("headerBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"true\""));
JavaFileAssert.assertThat(files.get("TestQueryParamsApi.java"))
.assertMethod("queryParamsTest")
.hasParameter("queryNumber").withType("BigDecimal")
.assertParameter("queryNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("queryString").withType("String")
.assertParameter("queryString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringWrapped").withType("String")
.assertParameter("queryStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotes").withType("String")
.assertParameter("queryStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotesWrapped").withType("String")
.assertParameter("queryStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryBoolean").withType("Boolean")
.assertParameter("queryBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("DefaultValue", ImmutableMap.of("value", "\"true\""));
}

View File

@ -250,53 +250,53 @@ public class JavaJerseyServerCodegenTest extends JavaJaxrsBaseTest {
JavaFileAssert.assertThat(files.get("TestHeadersApi.java"))
.assertMethod("headersTest")
.hasParameter("headerNumber").withType("BigDecimal")
.assertParameter("headerNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("headerString").withType("String")
.assertParameter("headerString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringWrapped").withType("String")
.assertParameter("headerStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotes").withType("String")
.assertParameter("headerStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerStringQuotesWrapped").withType("String")
.assertParameter("headerStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("headerBoolean").withType("Boolean")
.assertParameter("headerBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"true\""));
JavaFileAssert.assertThat(files.get("TestQueryParamsApi.java"))
.assertMethod("queryParamsTest")
.hasParameter("queryNumber").withType("BigDecimal")
.assertParameter("queryNumber").hasType("BigDecimal")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"11.2\""))
.toParameter().toMethod()
.hasParameter("queryString").withType("String")
.assertParameter("queryString").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringWrapped").withType("String")
.assertParameter("queryStringWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotes").withType("String")
.assertParameter("queryStringQuotes").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryStringQuotesWrapped").withType("String")
.assertParameter("queryStringQuotesWrapped").hasType("String")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"qwerty\\\"with quotes\\\" test\""))
.toParameter().toMethod()
.hasParameter("queryBoolean").withType("Boolean")
.assertParameter("queryBoolean").hasType("Boolean")
.assertParameterAnnotations()
.containsWithNameAndAttributes("ApiParam", ImmutableMap.of("defaultValue", "\"true\""));
}

View File

@ -3,18 +3,21 @@ package org.openapitools.codegen.java.micronaut;
import io.swagger.v3.oas.models.OpenAPI;
import io.swagger.v3.oas.models.info.Info;
import io.swagger.v3.oas.models.servers.Server;
import org.openapitools.codegen.*;
import org.openapitools.codegen.CliOption;
import org.openapitools.codegen.CodegenConstants;
import org.openapitools.codegen.DefaultGenerator;
import org.openapitools.codegen.config.CodegenConfigurator;
import org.openapitools.codegen.java.assertions.JavaFileAssert;
import org.openapitools.codegen.languages.JavaMicronautClientCodegen;
import org.testng.Assert;
import org.testng.annotations.Test;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.io.File;
import java.util.List;
import java.util.Map;
import static java.util.stream.Collectors.groupingBy;
import static org.openapitools.codegen.TestUtils.newTempFolder;
import static org.testng.Assert.assertEquals;
@ -323,27 +326,22 @@ public class JavaMicronautClientCodegenTest extends AbstractMicronautCodegenTest
* Includes regression tests for:
* - <a href="https://github.com/OpenAPITools/openapi-generator/issues/2417">Correct Jackson annotation when `wrapped: false`</a>
*/
@Test public void shouldGenerateCorrectXmlAnnotations() throws IOException {
@Test public void shouldGenerateCorrectXmlAnnotations() {
// Arrange
final String TEST_SPEC = "src/test/resources/3_0/java/xml-annotations-test.yaml";
final Path output = Files.createTempDirectory("test-xml-annotations_");
output.toFile().deleteOnExit();
JavaMicronautClientCodegen codegen = new JavaMicronautClientCodegen();
codegen.setWithXml(true);
codegen.setOutputDir(output.toString());
DefaultGenerator generator = new DefaultGenerator();
generator.setGeneratorPropertyDefault(CodegenConstants.MODELS, "true");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_TESTS, "false");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_DOCS, "false");
generator.setGenerateMetadata(false);
final CodegenConfigurator config = new CodegenConfigurator()
.addAdditionalProperty(CodegenConstants.WITH_XML, true)
.addGlobalProperty(CodegenConstants.MODELS, "Pet")
.addGlobalProperty(CodegenConstants.MODEL_DOCS, null)
.addGlobalProperty(CodegenConstants.MODEL_TESTS, null)
.setGeneratorName(JavaMicronautClientCodegen.NAME)
.setInputSpec("src/test/resources/3_0/java/xml-annotations-test.yaml")
.setOutputDir(newTempFolder().toString());
// Act
generator.opts(new ClientOptInput().config(codegen).openAPI(TestUtils.parseSpec(TEST_SPEC))).generate();
final List<File> files = new DefaultGenerator().opts(config.toClientOptInput()).generate();
// Assert
JavaFileAssert.assertThat(output.resolve("src/main/java/org/openapitools/model/Pet.java").toFile())
JavaFileAssert.assertThat(files.get(0))
.assertTypeAnnotations()
.containsWithNameAndAttributes("JacksonXmlRootElement", Map.of("localName", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
.containsWithNameAndAttributes("XmlRootElement", Map.of("name", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
@ -351,115 +349,115 @@ public class JavaMicronautClientCodegenTest extends AbstractMicronautCodegenTest
.toType()
// test custom-name on wrapper element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
.hasProperty("tags").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("tags").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Tag\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"TagList\""))
.toProperty().toType()
.assertMethod("getTags").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Tag\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"TagList\"", "useWrapping", "true"))
.toMethod().toFileAssert()
.assertMethod("getTags")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"Tag\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"TagList\"", "useWrapping", "true"))
.toFileAssert()
// custom internal xml-array element name, non-wrapped (1st example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("friends").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("friends").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"friend-pet\""))
.toProperty().toType()
.assertMethod("getFriends").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"friend-pet\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toMethod().toFileAssert()
.assertMethod("getFriends")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"friend-pet\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toFileAssert()
// test custom element name (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Change%20Element%20Names)
.hasProperty("status").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("status").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"PetStatus\""))
.toProperty().toType()
.assertMethod("getStatus").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"PetStatus\""))
.toMethod().toFileAssert()
.assertMethod("getStatus")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"PetStatus\""))
.toFileAssert()
// test same-name wrapping element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Wrapping%20Arrays)
// maps to 3rd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"photoUrls\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"photoUrls\""))
.toProperty().toType()
.assertMethod("getPhotoUrls").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"photoUrls\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"photoUrls\"", "useWrapping", "true"))
.toMethod().toFileAssert()
.assertMethod("getPhotoUrls")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"photoUrls\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"photoUrls\"", "useWrapping", "true"))
.toFileAssert()
// test attribute generation (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Convert%20Property%20to%20an%20Attribute)
.hasProperty("name").assertPropertyAnnotations()
.doesNotContainsWithName("XmlElement")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("name").assertPropertyAnnotations()
.doesNotContainWithName("XmlElement")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlAttribute", Map.of("name", "\"name\""))
.toProperty().toType()
.assertMethod("getName").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("isAttribute", "true", "localName", "\"name\""))
.toMethod().toFileAssert()
.assertMethod("getName")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("isAttribute", "true", "localName", "\"name\""))
.toFileAssert()
// test XML namespace and prefix (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Prefixes%20and%20Namespaces)
.hasProperty("id").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("id").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toProperty().toType()
.assertMethod("getId").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toMethod().toFileAssert()
.assertMethod("getId")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toFileAssert()
// external xml-array element name only (last example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("foods").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("foods").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"yummy-yummy\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"yummy-yummy\""))
.toProperty().toType()
.assertMethod("getFoods").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"yummy-yummy\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"yummy-yummy\""))
.toMethod().toFileAssert()
.assertMethod("getFoods")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"yummy-yummy\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"yummy-yummy\""))
.toFileAssert()
// internal xml-array element name (4th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("colors").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("colors").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"color\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"colors\""))
.toProperty().toType()
.assertMethod("getColors").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"color\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"colors\""))
.toMethod().toFileAssert()
.assertMethod("getColors")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"color\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"colors\""))
.toFileAssert()
// ignored external xml-array element name, non-wrapped (2nd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("categories").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("categories").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Category\""))
.toProperty().toType()
.assertMethod("getCategories").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Category\""))
.assertMethod("getCategories")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"Category\""))
// specific regression test for #2417: (useWrapping=false) needs to be present
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toMethod().toFileAssert()
.hasAnnotation("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toFileAssert()
// test custom-name on wrapper AND children (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
// maps to 5th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("activities").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("activities").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"item\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"activities-array\""))
.toProperty().toType()
.assertMethod("getActivities").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"item\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"activities-array\""));
.assertMethod("getActivities")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"item\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"activities-array\""));
}
}

View File

@ -3,18 +3,22 @@ package org.openapitools.codegen.java.micronaut;
import io.swagger.v3.oas.models.OpenAPI;
import io.swagger.v3.oas.models.info.Info;
import io.swagger.v3.oas.models.servers.Server;
import org.openapitools.codegen.*;
import org.openapitools.codegen.CliOption;
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.languages.JavaMicronautServerCodegen;
import org.testng.Assert;
import org.testng.annotations.Test;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.io.File;
import java.util.List;
import java.util.Map;
import static java.util.stream.Collectors.groupingBy;
import static org.openapitools.codegen.TestUtils.newTempFolder;
import static org.testng.Assert.assertEquals;
public class JavaMicronautServerCodegenTest extends AbstractMicronautCodegenTest {
@ -352,27 +356,22 @@ public class JavaMicronautServerCodegenTest extends AbstractMicronautCodegenTest
* Includes regression tests for:
* - <a href="https://github.com/OpenAPITools/openapi-generator/issues/2417">Correct Jackson annotation when `wrapped: false`</a>
*/
@Test public void shouldGenerateCorrectXmlAnnotations() throws IOException {
@Test public void shouldGenerateCorrectXmlAnnotations() {
// Arrange
final String TEST_SPEC = "src/test/resources/3_0/java/xml-annotations-test.yaml";
final Path output = Files.createTempDirectory("test-xml-annotations_");
output.toFile().deleteOnExit();
JavaMicronautServerCodegen codegen = new JavaMicronautServerCodegen();
codegen.setWithXml(true);
codegen.setOutputDir(output.toString());
DefaultGenerator generator = new DefaultGenerator();
generator.setGeneratorPropertyDefault(CodegenConstants.MODELS, "true");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_TESTS, "false");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_DOCS, "false");
generator.setGenerateMetadata(false);
final CodegenConfigurator config = new CodegenConfigurator()
.addAdditionalProperty(CodegenConstants.WITH_XML, true)
.addGlobalProperty(CodegenConstants.MODELS, "Pet")
.addGlobalProperty(CodegenConstants.MODEL_DOCS, null)
.addGlobalProperty(CodegenConstants.MODEL_TESTS, null)
.setGeneratorName(JavaMicronautServerCodegen.NAME)
.setInputSpec("src/test/resources/3_0/java/xml-annotations-test.yaml")
.setOutputDir(newTempFolder().toString());
// Act
generator.opts(new ClientOptInput().config(codegen).openAPI(TestUtils.parseSpec(TEST_SPEC))).generate();
final List<File> files = new DefaultGenerator().opts(config.toClientOptInput()).generate();
// Assert
JavaFileAssert.assertThat(output.resolve("src/main/java/org/openapitools/model/Pet.java").toFile())
JavaFileAssert.assertThat(files.get(0))
.assertTypeAnnotations()
.containsWithNameAndAttributes("JacksonXmlRootElement", Map.of("localName", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
.containsWithNameAndAttributes("XmlRootElement", Map.of("name", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
@ -380,115 +379,115 @@ public class JavaMicronautServerCodegenTest extends AbstractMicronautCodegenTest
.toType()
// test custom-name on wrapper element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
.hasProperty("tags").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("tags").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Tag\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"TagList\""))
.toProperty().toType()
.assertMethod("getTags").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Tag\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"TagList\"", "useWrapping", "true"))
.toMethod().toFileAssert()
.assertMethod("getTags")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"Tag\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"TagList\"", "useWrapping", "true"))
.toFileAssert()
// custom internal xml-array element name, non-wrapped (1st example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("friends").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("friends").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"friend-pet\""))
.toProperty().toType()
.assertMethod("getFriends").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"friend-pet\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toMethod().toFileAssert()
.assertMethod("getFriends")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"friend-pet\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toFileAssert()
// test custom element name (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Change%20Element%20Names)
.hasProperty("status").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("status").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"PetStatus\""))
.toProperty().toType()
.assertMethod("getStatus").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"PetStatus\""))
.toMethod().toFileAssert()
.assertMethod("getStatus")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"PetStatus\""))
.toFileAssert()
// test same-name wrapping element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Wrapping%20Arrays)
// maps to 3rd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("photoUrls").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"photoUrls\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"photoUrls\""))
.toProperty().toType()
.assertMethod("getPhotoUrls").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"photoUrls\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"photoUrls\"", "useWrapping", "true"))
.toMethod().toFileAssert()
.assertMethod("getPhotoUrls")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"photoUrls\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"photoUrls\"", "useWrapping", "true"))
.toFileAssert()
// test attribute generation (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Convert%20Property%20to%20an%20Attribute)
.hasProperty("name").assertPropertyAnnotations()
.doesNotContainsWithName("XmlElement")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("name").assertPropertyAnnotations()
.doesNotContainWithName("XmlElement")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlAttribute", Map.of("name", "\"name\""))
.toProperty().toType()
.assertMethod("getName").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("isAttribute", "true", "localName", "\"name\""))
.toMethod().toFileAssert()
.assertMethod("getName")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("isAttribute", "true", "localName", "\"name\""))
.toFileAssert()
// test XML namespace and prefix (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Prefixes%20and%20Namespaces)
.hasProperty("id").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("id").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toProperty().toType()
.assertMethod("getId").assertMethodAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toMethod().toFileAssert()
.assertMethod("getId")
.doesNotHaveAnnotation("JacksonXmlElementWrapper")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toFileAssert()
// external xml-array element name only (last example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("foods").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("foods").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"yummy-yummy\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"yummy-yummy\""))
.toProperty().toType()
.assertMethod("getFoods").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"yummy-yummy\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"yummy-yummy\""))
.toMethod().toFileAssert()
.assertMethod("getFoods")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"yummy-yummy\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"yummy-yummy\""))
.toFileAssert()
// internal xml-array element name (4th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("colors").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("colors").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"color\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"colors\""))
.toProperty().toType()
.assertMethod("getColors").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"color\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"colors\""))
.toMethod().toFileAssert()
.assertMethod("getColors")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"color\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"colors\""))
.toFileAssert()
// ignored external xml-array element name, non-wrapped (2nd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("categories").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.doesNotContainsWithName("XmlElementWrapper")
.assertProperty("categories").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.doesNotContainWithName("XmlElementWrapper")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"Category\""))
.toProperty().toType()
.assertMethod("getCategories").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Category\""))
.assertMethod("getCategories")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"Category\""))
// specific regression test for #2417: (useWrapping=false) needs to be present
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toMethod().toFileAssert()
.hasAnnotation("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toFileAssert()
// test custom-name on wrapper AND children (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
// maps to 5th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("activities").assertPropertyAnnotations()
.doesNotContainsWithName("XmlAttribute")
.assertProperty("activities").assertPropertyAnnotations()
.doesNotContainWithName("XmlAttribute")
.containsWithNameAndAttributes("XmlElement", Map.of("name", "\"item\""))
.containsWithNameAndAttributes("XmlElementWrapper", Map.of("name", "\"activities-array\""))
.toProperty().toType()
.assertMethod("getActivities").assertMethodAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"item\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"activities-array\""));
.assertMethod("getActivities")
.hasAnnotation("JacksonXmlProperty", Map.of("localName", "\"item\""))
.hasAnnotation("JacksonXmlElementWrapper", Map.of("localName", "\"activities-array\""));
}
}

View File

@ -1,17 +1,17 @@
package org.openapitools.codegen.languages;
import org.openapitools.codegen.ClientOptInput;
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.testng.annotations.Test;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.io.File;
import java.util.List;
import java.util.Map;
import static org.openapitools.codegen.TestUtils.newTempFolder;
public class JavaPKMSTServerCodegenTest {
/**
@ -20,27 +20,22 @@ public class JavaPKMSTServerCodegenTest {
* Includes regression tests for:
* - <a href="https://github.com/OpenAPITools/openapi-generator/issues/2417">Correct Jackson annotation when `wrapped: false`</a>
*/
@Test public void shouldGenerateCorrectXmlAnnotations() throws IOException {
@Test public void shouldGenerateCorrectXmlAnnotations() {
// Arrange
final String TEST_SPEC = "src/test/resources/3_0/java/xml-annotations-test.yaml";
final Path output = Files.createTempDirectory("test-xml-annotations_");
output.toFile().deleteOnExit();
JavaPKMSTServerCodegen codegen = new JavaPKMSTServerCodegen();
codegen.setWithXml(true);
codegen.setOutputDir(output.toString());
DefaultGenerator generator = new DefaultGenerator();
generator.setGeneratorPropertyDefault(CodegenConstants.MODELS, "true");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_TESTS, "false");
generator.setGeneratorPropertyDefault(CodegenConstants.MODEL_DOCS, "false");
generator.setGenerateMetadata(false);
final CodegenConfigurator config = new CodegenConfigurator()
.addAdditionalProperty(CodegenConstants.WITH_XML, true)
.addGlobalProperty(CodegenConstants.MODELS, "Pet")
.addGlobalProperty(CodegenConstants.MODEL_DOCS, null)
.addGlobalProperty(CodegenConstants.MODEL_TESTS, null)
.setGeneratorName("java-pkmst")
.setInputSpec("src/test/resources/3_0/java/xml-annotations-test.yaml")
.setOutputDir(newTempFolder().toString());
// Act
generator.opts(new ClientOptInput().config(codegen).openAPI(TestUtils.parseSpec(TEST_SPEC))).generate();
final List<File> files = new DefaultGenerator().opts(config.toClientOptInput()).generate();
// Assert
JavaFileAssert.assertThat(output.resolve("src/main/java/com/prokarma/pkmst/model/Pet.java").toFile())
JavaFileAssert.assertThat(files.get(0))
.assertTypeAnnotations()
.containsWithNameAndAttributes("JacksonXmlRootElement", Map.of("localName", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
.containsWithNameAndAttributes("XmlRootElement", Map.of("name", "\"Pet\"", "namespace", "\"urn:jacksonxml\""))
@ -48,56 +43,56 @@ public class JavaPKMSTServerCodegenTest {
.toType()
// test custom-name on wrapper element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
.hasProperty("tags").assertPropertyAnnotations()
.assertProperty("tags").assertPropertyAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Tag\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"TagList\"", "useWrapping", "true"))
.toProperty().toType()
// custom internal xml-array element name, non-wrapped (1st example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("friends").assertPropertyAnnotations()
.assertProperty("friends").assertPropertyAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"friend-pet\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
.toProperty().toType()
// test custom element name (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Change%20Element%20Names)
.hasProperty("status").assertPropertyAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.assertProperty("status").assertPropertyAnnotations()
.doesNotContainWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"PetStatus\""))
.toProperty().toType()
// test same-name wrapping element (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Wrapping%20Arrays)
// maps to 3rd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("photoUrls").assertPropertyAnnotations()
.assertProperty("photoUrls").assertPropertyAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"photoUrls\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"photoUrls\"", "useWrapping", "true"))
.toProperty().toType()
// test attribute generation (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Convert%20Property%20to%20an%20Attribute)
.hasProperty("name").assertPropertyAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.assertProperty("name").assertPropertyAnnotations()
.doesNotContainWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("isAttribute", "true", "localName", "\"name\""))
.toProperty().toType()
// test XML namespace and prefix (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Prefixes%20and%20Namespaces)
.hasProperty("id").assertPropertyAnnotations()
.doesNotContainsWithName("JacksonXmlElementWrapper")
.assertProperty("id").assertPropertyAnnotations()
.doesNotContainWithName("JacksonXmlElementWrapper")
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"id\"", "namespace", "\"http://example.com/schema\""))
.toProperty().toType()
// external xml-array element name only (last example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("foods").assertPropertyAnnotations()
.assertProperty("foods").assertPropertyAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"yummy-yummy\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"yummy-yummy\""))
.toProperty().toType()
// internal xml-array element name (4th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("colors").assertPropertyAnnotations()
.assertProperty("colors").assertPropertyAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"color\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"colors\""))
.toProperty().toType()
// ignored external xml-array element name, non-wrapped (2nd example in https://spec.openapis.org/oas/v3.0.0#xml-arrays)
.hasProperty("categories").assertPropertyAnnotations()
.assertProperty("categories").assertPropertyAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"Category\""))
// specific regression test for #2417: (useWrapping=false) needs to be present
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("useWrapping", "false"))
@ -105,8 +100,8 @@ public class JavaPKMSTServerCodegenTest {
// test custom-name on wrapper AND children (https://swagger.io/docs/specification/data-models/representing-xml/#:~:text=Use%20xml/name%20to%20give%20different%20names)
// maps to 5th example in https://spec.openapis.org/oas/v3.0.0#xml-arrays
.hasProperty("activities").assertPropertyAnnotations()
.assertProperty("activities").assertPropertyAnnotations()
.containsWithNameAndAttributes("JacksonXmlProperty", Map.of("localName", "\"item\""))
.containsWithNameAndAttributes("JacksonXmlElementWrapper", Map.of("localName", "\"activities-array\""));
}
}
}