serialize pattern localdatetime jsonformat example json spring jackson jodatime

json - pattern - Formato automático Jackson de Joda DateTime a formato ISO 8601



localdatetime json (4)

Según http://wiki.fasterxml.com/JacksonFAQDateHandling , "DateTime se puede serializar / deserializar automáticamente de forma similar a como se maneja java.util.Date". Sin embargo, no puedo lograr esta funcionalidad automática . Hay discusiones de StackOverflow relacionadas con este tema, pero la mayoría involucra una solución basada en código, pero en base a la cita anterior, debería ser capaz de lograr esto a través de una configuración simple.

Por http://wiki.fasterxml.com/JacksonFAQDateHandling Tengo mi configuración establecida para que las fechas de escritura como marcas de tiempo sean falsas. El resultado es que los tipos java.util.Date se serializan al formato ISO 8601, pero los tipos org.joda.time.DateTime se serializan a una representación de objetos largos.

Mi entorno es este:

Jackson 2.1
Joda time 2.1
Primavera 3.2
Java 1.6

La configuración de My Spring para jsonMapper Bean es

@Bean public ObjectMapper jsonMapper() { ObjectMapper objectMapper = new ObjectMapper(); //Fully qualified path shows I am using latest enum ObjectMapper.configure(com.fasterxml.jackson.databind.SerializationFeature. WRITE_DATES_AS_TIMESTAMPS , false); return objectMapper; }

Mi fragmento de código de prueba es este

Date d = new Date(); DateTime dt = new DateTime(d); //Joda time Map<String, Object> link = new LinkedHashMap<String, Object>(); link.put("date", d); link.put("createdDateTime", dt);

El fragmento resultante de salida JSON es este:

{"date":"2012-12-24T21:20:47.668+0000"} {"createdDateTime": {"year":2012,"dayOfMonth":24,"dayOfWeek":1,"era":1,"dayOfYear":359,"centuryOfEra":20,"yearOfEra":2012,"yearOfCentury":12,"weekyear":2012,"monthOfYear":12 *... remainder snipped for brevity*}}

Mi expectativa es que el objeto DateTime debe coincidir con el del objeto Date en función de la configuración. ¿Qué estoy haciendo mal o qué estoy malinterpretando? ¿Estoy leyendo demasiado en la palabra automáticamente de la documentación de Jackson y el hecho de que se produjo una representación de cadena, aunque no ISO 8601, está produciendo la funcionalidad automática anunciada?


En Spring Boot la configuración es aún más simple. Usted acaba de declarar la dependencia de Maven

<dependency> <groupId>com.fasterxml.jackson.datatype</groupId> <artifactId>jackson-datatype-joda</artifactId> </dependency>

y luego agregue el parámetro de configuración a su archivo application.yml / properties:

spring.jackson.serialization.write-dates-as-timestamps: false


Pensé en publicar un ejemplo de trabajo actualizado usando: Spring 4.2.0.RELEASE, Jackson 2.6.1, Joda 2.8.2

<?xml version="1.0" encoding="UTF-8"?> <beans:beans xmlns="http://www.springframework.org/schema/mvc" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:beans="http://www.springframework.org/schema/beans" xmlns:p="http://www.springframework.org/schema/p" xmlns:context="http://www.springframework.org/schema/context" xmlns:util="http://www.springframework.org/schema/util" xsi:schemaLocation="http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util.xsd "> <!-- DispatcherServlet Context: defines this servlet''s request-processing infrastructure --> <!-- Enables the Spring MVC @Controller programming model --> <annotation-driven> <message-converters> <beans:bean class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter"> <beans:property name="objectMapper" ref="objectMapper" /> </beans:bean> </message-converters> </annotation-driven> <!-- Handles HTTP GET requests for /resources/** by efficiently serving up static resources in the ${webappRoot}/resources directory --> <resources mapping="/resources/**" location="/resources/" /> <!-- Resolves views selected for rendering by @Controllers to .jsp resources in the /WEB-INF/views directory --> <beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver"> <beans:property name="prefix" value="/WEB-INF/views/" /> <beans:property name="suffix" value=".jsp" /> </beans:bean> <beans:bean id="objectMapper" class="org.springframework.http.converter.json.Jackson2ObjectMapperFactoryBean"> <beans:property name="featuresToDisable"> <beans:array> <util:constant static-field="com.fasterxml.jackson.databind.SerializationFeature.WRITE_DATES_AS_TIMESTAMPS" /> </beans:array> </beans:property> <beans:property name="modulesToInstall" value="com.fasterxml.jackson.datatype.joda.JodaModule" /> </beans:bean> <beans:bean id="localeResolver" class="org.springframework.web.servlet.i18n.SessionLocaleResolver"> <beans:property name="defaultLocale" value="en" /> </beans:bean> <!-- Configure the Message Locale Resources --> <beans:bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource"> <beans:property name="basename" value="errors" /> </beans:bean> <beans:bean id="versionSource" class="org.springframework.context.support.ResourceBundleMessageSource"> <beans:property name="basename" value="version" /> </beans:bean> <!-- DataSource --> <beans:bean id="dataSource" class="org.springframework.jndi.JndiObjectFactoryBean"> <beans:property name="jndiName" value="java:comp/env/jdbc/TestDB" /> </beans:bean> <!-- POJO: Configure the DAO Implementation --> <beans:bean id="publicationsDAO" class="com.test.api.publication.PublicationsDAOJdbcImpl"> <beans:property name="dataSource" ref="dataSource" /> </beans:bean> <!-- Things to auto-load --> <context:component-scan base-package="com.test.api" /> <context:component-scan base-package="com.test.rest" /> </beans:beans>

Código API

package com.test.api.publication; import java.util.Map; import com.fasterxml.jackson.annotation.JsonIgnoreProperties; import com.fasterxml.jackson.annotation.JsonProperty; import com.fasterxml.jackson.annotation.JsonRootName; @JsonRootName("event") @JsonIgnoreProperties(ignoreUnknown=true) public class Publication { private Map<String, Object> tokens; private String href; private String policy_path; @JsonProperty("tokens") public Map<String, Object> getTokens() { return tokens; } @JsonProperty("tokens") public void setTokens(Map<String, Object> tokens) { this.tokens = tokens; } @JsonProperty("href") public String getHref() { return href; } @JsonProperty("href") public void setHref(String href) { this.href = href; } @JsonProperty("policyPath") public String getPolicyPath() { return policy_path; } @JsonProperty("policyPath") public void setPolicyPath(String policy_path) { this.policy_path = policy_path; } } package com.test.api.publication; import javax.sql.DataSource; import org.slf4j.Logger; import org.slf4j.LoggerFactory; public class PublicationsDAOJdbcImpl implements PublicationsDAO{ static final Logger logger = LoggerFactory.getLogger(PublicationsDAOJdbcImpl.class.getName()); private DataSource _dataSource; @Override public void setDataSource(DataSource ds) { // TODO Auto-generated method stub } @Override public void close() { // TODO Auto-generated method stub } @Override public Publication getPublication(String policyPath) { Publication ret = new Publication(); //TODO: do something return ret; } } package com.test.rest.publication; import java.util.HashMap; import org.joda.time.DateTime; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.RestController; import com.test.api.publication.Publication; import com.test.api.publication.PublicationsDAO; import com.test.rest.error.UnknownResourceException; @RestController @RequestMapping("/pub") public class PublicationController { private static final Logger logger = LoggerFactory.getLogger(PublicationController.class); @Autowired @Qualifier("publicationsDAO") private PublicationsDAO publicationsDAO; /********************************************************************************************************************** * * @param policyPath * @return * @throws UnknownResourceException */ @RequestMapping(value = "/{policyPath}", method = RequestMethod.GET) public Publication getByPolicyPath(@PathVariable String policyPath) throws UnknownResourceException{ logger.debug("policyPath=" + policyPath); Publication ret = publicationsDAO.getPublication(policyPath); HashMap<String, Object> map = new HashMap<String, Object>(); map.put("TEST1", null); map.put("TEST2", new Integer(101)); map.put("TEST3", "QuinnZilla"); map.put("TEST4", new DateTime()); ret.setTokens(map); return ret; } }

Y obtengo el resultado de salida

{ "tokens": { "TEST2": 101, "TEST3": "QuinnZilla", "TEST4": "2015-10-06T16:59:35.120Z", "TEST1": null }, "href": null, "policyPath": null }


Pude obtener la respuesta a esto de la lista de correo de usuarios de Jackson, y quería compartir con ustedes ya que es un problema para novatos. Después de leer las preguntas frecuentes de Jackson Date, no me di cuenta de que se requieren dependencias adicionales y el registro, pero ese es el caso. Está documentado en la página del proyecto git hub aquí github.com/FasterXML/jackson-datatype-joda

Esencialmente, tuve que agregar otra dependencia a un jar de Jackson específico para el tipo de datos Joda, y luego tuve que registrar el uso de ese módulo en el mapeador de objetos. Los fragmentos de código están a continuación.

Para mi configuración de tipo de datos de Jackson Joda Maven, utilicé esto:

<dependency> <groupId>com.fasterxml.jackson.datatype</groupId> <artifactId>jackson-datatype-joda</artifactId> <version>${jackson.version}</version> </dependency>

Para registrar la función de serialización / deserialización de Joda utilicé esto:

ObjectMapper objectMapper = new ObjectMapper(); objectMapper.registerModule(new JodaModule()); objectMapper.configure(com.fasterxml.jackson.databind.SerializationFeature. WRITE_DATES_AS_TIMESTAMPS , false);


Usando Spring Boot.

Agregar a su configuración de Maven ...

<dependency> <groupId>com.fasterxml.jackson.datatype</groupId> <artifactId>jackson-datatype-joda</artifactId> <version>2.7.5</version> </dependency>

Luego a su configuración web ...

@Configuration public class WebConfiguration extends WebMvcConfigurerAdapter { public void configureMessageConverters(List<HttpMessageConverter<?>> converters) { final MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter(); final ObjectMapper objectMapper = new ObjectMapper(); //configure Joda serialization objectMapper.registerModule(new JodaModule()); objectMapper.configure( com.fasterxml.jackson.databind.SerializationFeature. WRITE_DATES_AS_TIMESTAMPS , false); // Other options such as how to deal with nulls or identing... objectMapper.setSerializationInclusion ( JsonInclude.Include.NON_NULL); objectMapper.enable(SerializationFeature.INDENT_OUTPUT); converter.setObjectMapper(objectMapper); converters.add(converter); super.configureMessageConverters(converters); } }