diff --git a/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/LinkVisitorContext.java b/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/LinkVisitorContext.java index 84a83fa..05dbec5 100644 --- a/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/LinkVisitorContext.java +++ b/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/LinkVisitorContext.java @@ -39,6 +39,7 @@ protected boolean isModel(JavaType type) { return type.getRawClass() != String.class && !isBoxedPrimitive(type) && !type.isPrimitive() + && !type.isEnumType() && !type.isMapLikeType() && !type.isCollectionLikeType(); } diff --git a/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Mapper.java b/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Mapper.java index b5198a1..828e493 100644 --- a/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Mapper.java +++ b/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Mapper.java @@ -15,13 +15,16 @@ */ package io.gravitee.maven.plugins.json.schema.generator.mojo; +import com.fasterxml.jackson.annotation.JsonProperty; import com.fasterxml.jackson.databind.JsonMappingException; import com.fasterxml.jackson.databind.ObjectMapper; +import com.fasterxml.jackson.databind.PropertyName; +import com.fasterxml.jackson.databind.introspect.Annotated; +import com.fasterxml.jackson.databind.introspect.JacksonAnnotationIntrospector; import com.fasterxml.jackson.module.jsonSchema.JsonSchema; import com.fasterxml.jackson.module.jsonSchema.customProperties.HyperSchemaFactoryWrapper; import com.fasterxml.jackson.module.jsonSchema.factories.SchemaFactoryWrapper; import io.gravitee.maven.plugins.json.schema.generator.util.ClassFinder; -import org.apache.maven.plugin.MojoExecutionException; import java.io.IOException; import java.nio.file.Path; @@ -49,6 +52,22 @@ public Mapper(Config config) { this.config = config; } + /** + * WRITE_ONLY fields are no output to the schema. This is incorrect. + * From https://stackoverflow.com/a/55064740/3351474 + */ + private class IgnoreJacksonWriteOnlyAccess extends JacksonAnnotationIntrospector { + + @Override + public JsonProperty.Access findPropertyAccess(Annotated m) { + JsonProperty.Access access = super.findPropertyAccess(m); + if (access == JsonProperty.Access.WRITE_ONLY) { + return JsonProperty.Access.AUTO; + } + return access; + } + } + /** * Generates JSON Schemas from the matched Class names * @@ -58,21 +77,30 @@ public List generateJsonSchemas() { final List generatedSchemas = new ArrayList<>(); ObjectMapper mapper = new ObjectMapper(); + mapper.setAnnotationIntrospector(new IgnoreJacksonWriteOnlyAccess()); SchemaFactoryWrapper schemaVisitor = new HyperSchemaFactoryWrapper(); schemaVisitor.setVisitorContext(new LinkVisitorContext()); for (String className : generateClassNames()) { try { + Class _class = getClass().getClassLoader().loadClass(className); try { - mapper.acceptJsonFormatVisitor(mapper.constructType( - getClass().getClassLoader().loadClass(className) - ), schemaVisitor); + mapper.acceptJsonFormatVisitor(mapper.constructType(_class), schemaVisitor); } catch (JsonMappingException e) { throw new GenerationException("Unable to format class " + className, e); } JsonSchema schema = schemaVisitor.finalSchema(); if (schema == null) { - throw new IllegalArgumentException("Could not build schema or find any classes."); + throw new IllegalArgumentException("Could not build schema for class "+className); + } + if (schema.getId() == null) { + if (_class.isEnum()) { + config.getLogger().info("Skipping enum class " + className + " (will be included directly in referenced schema)"); + } + else { + config.getLogger().warn("Ignoring schema for class " + className); + } + continue; } generatedSchemas.add(schema); } catch (GenerationException | ClassNotFoundException e) { diff --git a/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Output.java b/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Output.java index 2fe0070..203e548 100644 --- a/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Output.java +++ b/src/main/java/io/gravitee/maven/plugins/json/schema/generator/mojo/Output.java @@ -95,7 +95,7 @@ private void createJsonFile(JsonSchema schema) { config.getLogger().info("Created JSON Schema: " + outputPath.normalize().toAbsolutePath().toString()); } catch (JsonProcessingException e) { config.getLogger().warn("Unable to display schema " + schema.getId(), e); - } catch (IOException e) { + } catch (Exception e) { config.getLogger().warn("Unable to write Json file for schema " + schema.getId(), e); } } diff --git a/src/test/java/io/gravitee/maven/plugins/json/schema/generator/mojo/MapperTest.java b/src/test/java/io/gravitee/maven/plugins/json/schema/generator/mojo/MapperTest.java index ec557e6..0aa95c7 100644 --- a/src/test/java/io/gravitee/maven/plugins/json/schema/generator/mojo/MapperTest.java +++ b/src/test/java/io/gravitee/maven/plugins/json/schema/generator/mojo/MapperTest.java @@ -26,6 +26,7 @@ import java.io.File; import java.util.Arrays; +import java.util.HashSet; import java.util.List; import java.util.Map; @@ -69,7 +70,7 @@ public void testGenerateJsonSchemasWithNoBean() throws Exception { mapper = new Mapper(new Config(new Globs(Arrays.asList("NoBean.class"), null), BUILD_DIRECTORY, null, LOG)); List schemas = mapper.generateJsonSchemas(); - Assert.assertFalse(schemas.isEmpty()); + Assert.assertTrue(schemas.isEmpty()); } @Test @@ -94,14 +95,9 @@ public void testGenerateJsonSchemasWithBeanByUsingExternalDependency() throws Ex Assert.assertEquals(1, properties.size()); JsonSchema stringSchema = properties.get("jsonFormatTypes"); - Assert.assertEquals(JsonFormatTypes.OBJECT, stringSchema.getType()); - /* - Assert.assertEquals(JsonFormatTypes.OBJECT, stringSchema.getType()); - Assert.assertEquals( - "jsonFormatTypes", - stringSchema.getId().substring(stringSchema.getId().lastIndexOf(":") + 1, stringSchema.getId().length()) - ); - */ + Assert.assertEquals(JsonFormatTypes.STRING, stringSchema.getType()); + Assert.assertEquals(new HashSet<>(Arrays.asList("string", "number", "integer", + "boolean", "object", "array", "null", "any")), stringSchema.asValueTypeSchema().getEnums()); }