Last active
September 26, 2022 11:10
-
-
Save dschulten/4718b60b95bf9253dab8009febfa6d24 to your computer and use it in GitHub Desktop.
Set default timezone of jax-rs jackson provider for deserialization of timestamp to XmlGregorianCalendar JAXB date field.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package de.kommone.kmc.api; | |
import java.util.TimeZone; | |
import javax.ws.rs.Produces; | |
import javax.ws.rs.ext.ContextResolver; | |
import javax.ws.rs.ext.Provider; | |
import com.fasterxml.jackson.databind.ObjectMapper; | |
@Provider | |
@Produces("application/json") | |
public class JacksonConfigurator implements ContextResolver<ObjectMapper> { | |
private ObjectMapper mapper = new ObjectMapper(); | |
public JacksonConfigurator() { | |
mapper.setTimeZone(TimeZone.getTimeZone("Europe/Berlin")); | |
} | |
@Override | |
public ObjectMapper getContext(Class<?> arg0) { | |
return mapper; | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
... | |
<dependency> | |
<groupId>org.glassfish.jersey.containers</groupId> | |
<artifactId>jersey-container-servlet</artifactId> | |
<version>2.25.1</version> | |
<exclusions> | |
<exclusion> | |
<groupId>org.glassfish.jersey.media</groupId> | |
<artifactId>jersey-media-jaxb</artifactId> | |
</exclusion> | |
</exclusions> | |
</dependency> | |
<dependency> | |
<groupId>org.glassfish.jersey.media</groupId> | |
<artifactId>jersey-media-json-jackson</artifactId> | |
<version>2.25.1</version> | |
</dependency> | |
... |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<servlet> | |
<servlet-name>javax.ws.rs.core.Application</servlet-name> | |
<load-on-startup>1</load-on-startup> | |
</servlet> | |
<servlet-mapping> | |
<servlet-name>javax.ws.rs.core.Application</servlet-name> | |
<url-pattern>/api/*</url-pattern> | |
</servlet-mapping> |
Hi,
Just doing that, the JacksonConfigurator constructor is called, but getContext() method is never called.
What could be a problem?
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
The default jax-rs jackson provider uses UTC as timezone, so that a date which has been parsed from a String representation in a different timezone and serialized as JSON timestamp gets deserialized with a wrong offset by the jax-rs service. The root problem is of course that the source system uses its local timezone to parse a date string into a timestamp. But if you cannot fix that, here is how you can compensate.
Scenario:
org.glassfish.jersey.mediajersey-media-json-jackson
serializerXMLGregorianCalendar
, regardless of the system timezoneThis code allows to specify the timezone which should be used by Jackson when creating a timezoned date type like
XMLGregorianCalendar
from a JSON timestamp value. The@Provider
annotation activates the custom resolver forObjectMapper
, which injects the customizedObjectMapper
, if class scanning is active.The
ObjectMapper
can be fully customized with custom deserializers, date format and other configuration items likeInclusion.NON_NULL
, see https://stackoverflow.com/a/5234682/743507 for an example.Note: If a custom jax-rs
Application
annotated with@ApplicationPath
is present to support annotation-only setup without web.xml, but it overridesgetClasses
orgetSingleton
, then class scanning is deactivated as hinted by section 2.3.2 of the jax-rs spec.I.e. in that case you have to return the
JacksonConfigurator
as one of the classes returned bygetClasses
. Otherwise your resource classes will not be picked up and you get 404 when sending requests.Related code:
com.fasterxml.jackson.databind.ext.CoreXMLDeserializers.Std#_gregorianFromDate