From de8b33dc771282660fcd703991c2c8317300b129 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lo=C3=AFc=20Mathieu?= Date: Mon, 2 Sep 2019 14:53:25 +0200 Subject: [PATCH] feat: add Jackson serder --- .../main/asciidoc/mongodb-panache-guide.adoc | 26 ++--------------- .../deployment/PanacheResourceProcessor.java | 10 +++++-- .../panache/mongodb-panache/runtime/pom.xml | 7 +++++ .../panache/jackson/ObjectIdDeserializer.java | 23 +++++++++++++++ .../panache/jackson/ObjectIdSerializer.java | 20 +++++++++++++ .../panache/jackson/ObjectMapperProducer.java | 28 +++++++++++++++++++ .../deployment/ResteasyJacksonProcessor.java | 2 +- .../smallrye-opentracing/deployment/pom.xml | 2 +- .../SmallRyeOpenTracingProcessor.java | 2 +- extensions/spring-web/deployment/pom.xml | 4 +++ .../web/deployment/SpringWebProcessor.java | 2 +- 11 files changed, 96 insertions(+), 30 deletions(-) create mode 100644 extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdDeserializer.java create mode 100644 extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdSerializer.java create mode 100644 extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectMapperProducer.java diff --git a/docs/src/main/asciidoc/mongodb-panache-guide.adoc b/docs/src/main/asciidoc/mongodb-panache-guide.adoc index d0810994da4f6b..853540ce215aaa 100644 --- a/docs/src/main/asciidoc/mongodb-panache-guide.adoc +++ b/docs/src/main/asciidoc/mongodb-panache-guide.adoc @@ -448,31 +448,9 @@ you need to provide the value by yourself. ==== `ObjectId` can be difficult to use if you want to expose its value in your rest service. -So we create JSON-B providers to serialize/deserialize them as String. -These providers are not registered by default so you need to register them with a JAX-RS `ContextResolver`: +So we create JSON-B providers to serialize/deserialize them as String and also Jackson equivalent. -[source,java] --- -import javax.json.bind.Jsonb; -import javax.json.bind.JsonbBuilder; -import javax.json.bind.JsonbConfig; -import javax.ws.rs.ext.ContextResolver; -import javax.ws.rs.ext.Provider; - -import io.quarkus.mongodb.panache.jsonb.ObjectIdDeserializer; -import io.quarkus.mongodb.panache.jsonb.ObjectIdSerializer; - -@Provider -public class QuarkusJsonbContextResolver implements ContextResolver { - - public Jsonb getContext(Class clazz) { - JsonbConfig config = new JsonbConfig(); - config.withSerializers(new ObjectIdSerializer()).withDeserializers(new ObjectIdDeserializer()); - return JsonbBuilder.create(config); - } - -} --- +JSON-B providers and Jackson serializer/deserializer are automatically registered as soon as one of Resteasy with JSON-B or Resteasy with Jackson extensions are used. == How and why we simplify MongoDB API diff --git a/extensions/panache/mongodb-panache/deployment/src/main/java/io/quarkus/mongodb/panache/deployment/PanacheResourceProcessor.java b/extensions/panache/mongodb-panache/deployment/src/main/java/io/quarkus/mongodb/panache/deployment/PanacheResourceProcessor.java index cbd5b818f3313e..a42272210a5193 100644 --- a/extensions/panache/mongodb-panache/deployment/src/main/java/io/quarkus/mongodb/panache/deployment/PanacheResourceProcessor.java +++ b/extensions/panache/mongodb-panache/deployment/src/main/java/io/quarkus/mongodb/panache/deployment/PanacheResourceProcessor.java @@ -14,8 +14,6 @@ import io.quarkus.deployment.Capabilities; import io.quarkus.deployment.annotations.BuildProducer; import io.quarkus.deployment.annotations.BuildStep; -import io.quarkus.deployment.annotations.ExecutionTime; -import io.quarkus.deployment.annotations.Record; import io.quarkus.deployment.builditem.ApplicationIndexBuildItem; import io.quarkus.deployment.builditem.BytecodeTransformerBuildItem; import io.quarkus.deployment.builditem.CombinedIndexBuildItem; @@ -26,6 +24,7 @@ import io.quarkus.mongodb.panache.PanacheMongoEntityBase; import io.quarkus.mongodb.panache.PanacheMongoRepository; import io.quarkus.mongodb.panache.PanacheMongoRepositoryBase; +import io.quarkus.mongodb.panache.jackson.ObjectMapperProducer; import io.quarkus.mongodb.panache.jsonb.PanacheMongoJsonbContextResolver; import io.quarkus.panache.common.deployment.PanacheFieldAccessEnhancer; import io.quarkus.resteasy.common.spi.ResteasyJaxrsProviderBuildItem; @@ -44,6 +43,13 @@ FeatureBuildItem featureBuildItem() { } @BuildStep + AdditionalBeanBuildItem registerJacksonSerDer(Capabilities capabilities) { + if (capabilities.isCapabilityPresent("io.quarkus.resteasy.jackson")) { + return new AdditionalBeanBuildItem(ObjectMapperProducer.class); + } + return null; + } + @BuildStep ResteasyJaxrsProviderBuildItem registerJsonbSerDer(Capabilities capabilities) { if (capabilities.isCapabilityPresent("io.quarkus.resteasy.jsonb")) { diff --git a/extensions/panache/mongodb-panache/runtime/pom.xml b/extensions/panache/mongodb-panache/runtime/pom.xml index 3a3add6c045019..675108f517ea93 100644 --- a/extensions/panache/mongodb-panache/runtime/pom.xml +++ b/extensions/panache/mongodb-panache/runtime/pom.xml @@ -37,6 +37,13 @@ quarkus-resteasy-jsonb true + + + + io.quarkus + quarkus-resteasy-jackson + true + org.junit.jupiter junit-jupiter diff --git a/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdDeserializer.java b/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdDeserializer.java new file mode 100644 index 00000000000000..153959cea58a7f --- /dev/null +++ b/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdDeserializer.java @@ -0,0 +1,23 @@ +package io.quarkus.mongodb.panache.jackson; + +import java.io.IOException; + +import org.bson.types.ObjectId; + +import com.fasterxml.jackson.core.JsonParser; +import com.fasterxml.jackson.core.JsonProcessingException; +import com.fasterxml.jackson.databind.DeserializationContext; +import com.fasterxml.jackson.databind.JsonDeserializer; + +public class ObjectIdDeserializer extends JsonDeserializer { + + @Override + public ObjectId deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) + throws IOException, JsonProcessingException { + String value = jsonParser.getValueAsString(); + if (value != null) { + return new ObjectId(value); + } + return null; + } +} diff --git a/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdSerializer.java b/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdSerializer.java new file mode 100644 index 00000000000000..b474976094f9a9 --- /dev/null +++ b/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectIdSerializer.java @@ -0,0 +1,20 @@ +package io.quarkus.mongodb.panache.jackson; + +import java.io.IOException; + +import org.bson.types.ObjectId; + +import com.fasterxml.jackson.core.JsonGenerator; +import com.fasterxml.jackson.databind.JsonSerializer; +import com.fasterxml.jackson.databind.SerializerProvider; + +public class ObjectIdSerializer extends JsonSerializer { + + @Override + public void serialize(ObjectId objectId, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) + throws IOException { + if (objectId != null) { + jsonGenerator.writeString(objectId.toString()); + } + } +} diff --git a/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectMapperProducer.java b/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectMapperProducer.java new file mode 100644 index 00000000000000..2d08397c8cd0b4 --- /dev/null +++ b/extensions/panache/mongodb-panache/runtime/src/main/java/io/quarkus/mongodb/panache/jackson/ObjectMapperProducer.java @@ -0,0 +1,28 @@ +package io.quarkus.mongodb.panache.jackson; + +import javax.enterprise.context.ApplicationScoped; +import javax.enterprise.inject.Produces; +import javax.inject.Singleton; + +import org.bson.types.ObjectId; + +import com.fasterxml.jackson.databind.ObjectMapper; +import com.fasterxml.jackson.databind.module.SimpleModule; + +/** + * This ObjectMapperProducer will produce an ObjectMapper that will override the default one from resteasy-jackson. + */ +@ApplicationScoped +public class ObjectMapperProducer { + + @Singleton + @Produces + public ObjectMapper objectMapper() { + ObjectMapper objectMapper = new ObjectMapper(); + SimpleModule module = new SimpleModule("ObjectIdModule"); + module.addSerializer(ObjectId.class, new ObjectIdSerializer()); + module.addDeserializer(ObjectId.class, new ObjectIdDeserializer()); + objectMapper.registerModule(module); + return objectMapper; + } +} diff --git a/extensions/resteasy-jackson/deployment/src/main/java/io/quarkus/resteasy/jackson/deployment/ResteasyJacksonProcessor.java b/extensions/resteasy-jackson/deployment/src/main/java/io/quarkus/resteasy/jackson/deployment/ResteasyJacksonProcessor.java index 1aedc8431824a9..90851fe4a3e44b 100644 --- a/extensions/resteasy-jackson/deployment/src/main/java/io/quarkus/resteasy/jackson/deployment/ResteasyJacksonProcessor.java +++ b/extensions/resteasy-jackson/deployment/src/main/java/io/quarkus/resteasy/jackson/deployment/ResteasyJacksonProcessor.java @@ -49,7 +49,7 @@ public class ResteasyJacksonProcessor { private static final String QUARKUS_CONTEXT_RESOLVER_NAME = "io.quarkus.resteasy.jackson.runtime.QuarkusObjectMapperContextResolver"; - @BuildStep + @BuildStep(providesCapabilities = "io.quarkus.resteasy.jackson") void build(BuildProducer feature) { feature.produce(new FeatureBuildItem(FeatureBuildItem.RESTEASY_JACKSON)); } diff --git a/extensions/smallrye-opentracing/deployment/pom.xml b/extensions/smallrye-opentracing/deployment/pom.xml index f96c0923ac6bc5..d4c733eb32b0e5 100644 --- a/extensions/smallrye-opentracing/deployment/pom.xml +++ b/extensions/smallrye-opentracing/deployment/pom.xml @@ -20,7 +20,7 @@ io.quarkus - quarkus-resteasy-deployment + quarkus-resteasy-common-spi io.quarkus diff --git a/extensions/smallrye-opentracing/deployment/src/main/java/io/quarkus/smallrye/opentracing/deployment/SmallRyeOpenTracingProcessor.java b/extensions/smallrye-opentracing/deployment/src/main/java/io/quarkus/smallrye/opentracing/deployment/SmallRyeOpenTracingProcessor.java index 6febabe68d625c..67088164111649 100644 --- a/extensions/smallrye-opentracing/deployment/src/main/java/io/quarkus/smallrye/opentracing/deployment/SmallRyeOpenTracingProcessor.java +++ b/extensions/smallrye-opentracing/deployment/src/main/java/io/quarkus/smallrye/opentracing/deployment/SmallRyeOpenTracingProcessor.java @@ -12,7 +12,7 @@ import io.quarkus.deployment.annotations.BuildStep; import io.quarkus.deployment.builditem.FeatureBuildItem; import io.quarkus.deployment.builditem.substrate.ReflectiveMethodBuildItem; -import io.quarkus.resteasy.common.deployment.ResteasyJaxrsProviderBuildItem; +import io.quarkus.resteasy.common.spi.ResteasyJaxrsProviderBuildItem; import io.quarkus.smallrye.opentracing.runtime.QuarkusSmallRyeTracingDynamicFeature; import io.quarkus.smallrye.opentracing.runtime.TracerProducer; import io.quarkus.undertow.deployment.FilterBuildItem; diff --git a/extensions/spring-web/deployment/pom.xml b/extensions/spring-web/deployment/pom.xml index eab1911372a7e8..698870743b80e9 100644 --- a/extensions/spring-web/deployment/pom.xml +++ b/extensions/spring-web/deployment/pom.xml @@ -27,6 +27,10 @@ io.quarkus quarkus-resteasy-deployment + + io.quarkus + quarkus-resteasy-common-spi + io.quarkus quarkus-undertow-deployment diff --git a/extensions/spring-web/deployment/src/main/java/io/quarkus/spring/web/deployment/SpringWebProcessor.java b/extensions/spring-web/deployment/src/main/java/io/quarkus/spring/web/deployment/SpringWebProcessor.java index 33ffbf6808840e..448b556da27045 100644 --- a/extensions/spring-web/deployment/src/main/java/io/quarkus/spring/web/deployment/SpringWebProcessor.java +++ b/extensions/spring-web/deployment/src/main/java/io/quarkus/spring/web/deployment/SpringWebProcessor.java @@ -35,7 +35,7 @@ import io.quarkus.deployment.util.ServiceUtil; import io.quarkus.gizmo.ClassOutput; import io.quarkus.resteasy.common.deployment.ResteasyCommonProcessor; -import io.quarkus.resteasy.common.deployment.ResteasyJaxrsProviderBuildItem; +import io.quarkus.resteasy.common.spi.ResteasyJaxrsProviderBuildItem; import io.quarkus.resteasy.server.common.deployment.AdditionalJaxRsResourceDefiningAnnotationBuildItem; import io.quarkus.resteasy.server.common.deployment.AdditionalJaxRsResourceMethodAnnotationsBuildItem; import io.quarkus.resteasy.server.common.deployment.AdditionalJaxRsResourceMethodParamAnnotations;