【问题标题】:spring boot Joda DateTime Serialisationspring boot Joda DateTime 序列化
【发布时间】:2015-01-11 15:01:22
【问题描述】:

我正在尝试使用 Spring Boot v1.2.0.BUILD-SNAPSHOT 将 Joda DateTime 属性序列化为 ISO-8601 这是我非常简单的 REST 应用程序。

@RestController
@Configuration
@ComponentScan
@EnableAutoConfiguration
public class Application {

    class Info{

       private DateTime dateTime;

        public Info(){
            dateTime = new DateTime();
        }
        public DateTime getDateTime() {
           return dateTime;
        }

        public void setDateTime(DateTime dateTime) {
           this.dateTime = dateTime;
        }
    }

    @RequestMapping("/info")
    Info info() {
        return new Info();
    }

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }

    @Bean
   public Module getModule(){
        return new JodaModule();
   }
}

dateTime 被序列化为时间戳,例如{"dateTime":1415954873412} 我试过添加

@Bean
@Primary
public ObjectMapper getObjectMapper() {
    ObjectMapper objectMapper = new ObjectMapper();
    objectMapper.configure(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS,
                false);
    return objectMapper;
}

但这也无济于事。那么如何在 Spring Boot 中配置 Jackson 以使用 ISO-8601 格式进行序列化呢? 顺便说一句:我只在我的 Gradle 构建中添加了以下依赖项

compile("joda-time:joda-time:2.4")
compile("org.jadira.usertype:usertype.jodatime:2.0.1")
compile("com.fasterxml.jackson.datatype:jackson-datatype-joda:2.4.2");

【问题讨论】:

    标签: datetime jackson jodatime spring-boot iso8601


    【解决方案1】:

    还有一个 joda-date-time-format 属性(我认为这个属性第一次出现在 Spring boot 1.3.x 版本中)你可以在你的 application.properties 中设置它适用于 jackson 序列化/反序列化:

    发件人:https://docs.spring.io/spring-boot/docs/current/reference/html/common-application-properties.html

    spring.jackson.joda-date-time-format= # Joda date time format string. If not configured, "date-format" will be used as a fallback if it is configured with a format string.
    

    所以如果你想使用 ISO 格式你可以这样设置:

    spring.jackson.joda-date-time-format=yyyy-MM-dd'T'HH:mm:ss.SSSZ
    

    您可以使用不同数量的“Z”来更改时区 ID 或偏移小时数的显示方式,来自 joda 时间文档 (http://joda-time.sourceforge.net/apidocs/org/joda/time/format/DateTimeFormat.html):

    Zone: 'Z' outputs offset without a colon, 'ZZ' outputs the offset with a colon, 'ZZZ' or more outputs the zone id.
    

    【讨论】:

      【解决方案2】:

      将此添加到您资源中的application.*。 (我使用 yamel,所以它对我来说是 .yml,但默认情况下应该是 .properties

      spring.jackson.date-format: yyyy-MM-dd'T'HH:mm:ssZ
      

      或者你想要的任何格式。

      【讨论】:

        【解决方案3】:

        使用 Spring Boot 1.2,您可以使用流畅的 builder 构建 ObjectMapper 实例:

        @Bean
        public ObjectMapper objectMapper(Jackson2ObjectMapperBuilder builder) {
            return builder
                      .featuresToDisable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS)
                      .build();
        }
        

        至于JodaModule,当com.fasterxml.jackson.datatype:jackson-datatype-joda在类路径上时会自动配置。

        【讨论】:

          【解决方案4】:

          由于您使用的是 Spring Boot 1.2,您应该能够简单地将以下内容添加到您的 application.properties 文件中:

          spring.jackson.serialization.write_dates_as_timestamps=false
          

          这将以以下形式给出输出:

          {
              "dateTime": "2014-11-18T19:01:38.352Z"
          }
          

          如果您需要自定义格式,您可以直接配置JodaModule,例如删除时间部分:

          @Bean
          public JodaModule jacksonJodaModule() {
              JodaModule module = new JodaModule();
              DateTimeFormatterFactory formatterFactory = new DateTimeFormatterFactory();
              formatterFactory.setIso(ISO.DATE);
              module.addSerializer(DateTime.class, new DateTimeSerializer(
                  new JacksonJodaFormat(formatterFactory.createDateTimeFormatter()
                      .withZoneUTC())));
              return module;
          }
          

          【讨论】:

          • 我已经尝试了以下每个都没有成功 1.将其添加到 application.properties 文件 spring.jackson.serialization.write_dates_as_timestamps=false 2.如下创建一个 bean @Bean public Module getModule() { 返回新的 JodaModule(); 3. 自动装配 ObjectMapper 并设置 objectMapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);唯一有效的方法是注释属性 @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSSZ")
          • 为我工作。我已经将我的示例推送到 GitHub github.com/philwebb/stackoverflow-26926289
          • 谢谢你 - 我让它工作了。我正在使用 compile("org.springframework.boot:spring-boot-starter-data-rest") 但它适用于: compile("org.springframework.boot:spring-boot-starter-web") 这是一个错误还是一个功能? :)
          • 并不是说你也会在你的 pom 中看到工件 jackson-datatype-joda
          • 很高兴您在 GitHub @PhilWebb 上发布了示例代码。帮助我意识到我在尝试序列化的类中必须使用 org.joda.time.DateTime 而不是 java.util.Date ......以使此配置正常工作。 (值得注意的是,Swagger 代码自动生成 - 针对 Spring - 使用 java.util.Date 而不是 joda DateTime 类)。 更新 实际上并不积极我已经想通了,但是嘿。以为我会分享,以防它是图片的一部分。
          【解决方案5】:

          new JodaModule() 传递给对象映射器的构造函数。

          使用 ISO 模式注释您的 Info 方法

          @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSSZ")
          

          或者我认为如果您使用的是 spring,您可以使用它

          @JsonFormat(shape = JsonFormat.Shape.STRING, pattern = DateTimeFormat.ISO.DATE_TIME)
          

          【讨论】:

          • 你也可以调用 .setSimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSSZ");在您的对象映射器上而不是注释类。
          • 唯一有效的是如果我使用注释,即@JsonFormat(shape = JsonFormat.Shape.STRING, pattern = "yyyy-MM-dd'T'HH:mm:ss.SSSZ" ) 必须有某种方法可以启用所有 DateTime 属性。我不想注释所有的属性
          • 不确定是否有帮助,但可能值得升级到最新版本 2.4.3。另外:如果@JsonFormat 覆盖有效,但SerializationFeature.WRITE_DATES_AS_TIMESTAMPS 无效,我会针对该模块提交一个错误——它应该按您期望的方式工作。
          • 2.4.3 没有帮助。我尝试了几种方法,但注意工作。我的印象是 SpringBoot 使用的 ObjectMapper 实例与我尝试配置的实例不同。这对我来说似乎是一个错误,但我在几个线程中读到这应该只是添加 JodaModule 的一个案例
          • 根据文档(§63.3 Customize the Jackson ObjectMapper)应该可以配置 application.properties spring.jackson.serialization.write_dates_as_timestamps=false
          猜你喜欢
          • 2015-06-20
          • 1970-01-01
          • 2014-04-14
          • 2015-02-10
          • 2015-10-06
          • 1970-01-01
          • 1970-01-01
          • 2011-08-07
          • 2018-03-14
          相关资源
          最近更新 更多