当前位置:   article > 正文

springboot 全局配置时间格式化_spring boot localdatedeserializer

spring boot localdatedeserializer

springboot 全局配置时间格式化

web项目中,后台服务返回给前端的时间格式若未配置,则返回的数据可能是时间戳或者数组,例子如下:

entity 类型LocalDateTime

  1. {
  2. "id": 5,
  3. "name": null,
  4. "age": null,
  5. "jsonStr": null,
  6. "ct": "2020-08-04T14:56:54.971"
  7. }

entity 类型为Date,时间为时间戳

  1. {
  2. "id": 5,
  3. "ct": 1596524214971
  4. }

若需要显示yyyy-MM-dd HH:mm:ss时间格式时,可以在对应的属性上配置@JsonFormat注解:例如:

  1. @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
  2. private Date ct;

还可以支持

  1. @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
  2. private LocalDateTime ct;

若系统内时间属性字段相对多了之后,会多次配置,也会比较麻烦,所以需要进行全局配置

若时间属性字段为Date类型时,可直接在配置文件中配置如下配置:

spring.jackson.date-formate=yyyy-MM-dd HH:mm:ss

若时间属性为JDK1.8以后的接口时,此配置就不生效了。为解决这个查看了spring-boot的实现方式。

spring-boot提供了JacksonAutoConfiguration自动配置相关类,观察源码:

  1. private void configureDateFormat(Jackson2ObjectMapperBuilder builder) {
  2. String dateFormat = this.jacksonProperties.getDateFormat();
  3. if(dateFormat != null) {
  4. try {
  5. Class ex = ClassUtils.forName(dateFormat, (ClassLoader)null);
  6. builder.dateFormat((DateFormat)BeanUtils.instantiateClass(ex));
  7. } catch (ClassNotFoundException var6) {
  8. SimpleDateFormat simpleDateFormat = new SimpleDateFormat(dateFormat);
  9. TimeZone timeZone = this.jacksonProperties.getTimeZone();
  10. if(timeZone == null) {
  11. timeZone = (new ObjectMapper()).getSerializationConfig().getTimeZone();
  12. }
  13. simpleDateFormat.setTimeZone(timeZone);
  14. builder.dateFormat(simpleDateFormat);
  15. }
  16. }
  17. }
  1. @ConfigurationProperties(
  2. prefix = "spring.jackson"
  3. )
  4. public class JacksonProperties {
  5. private String dateFormat;
  6. }

查看源码可知,当配置spring.jackson.date-formate属性时,若配置为类路径,则初始化格式化类,进行处理。若配置的不为类路径时,采用SimpleDateFormat类进行格式化时间,而SimpleDateFormat这个类只能对Date类型的时间格式化,所以当采用JDK1.8版本以后的时间接口时,会出现配置失效的问题。

当查看JacksonAutoConfiguration源码时:

  1. @Configuration(
  2. proxyBeanMethods = false
  3. )
  4. @ConditionalOnClass({ObjectMapper.class})
  5. public class JacksonAutoConfiguration {
  6. ...
  7. }

JacksonAutoConfiguration类配置了条件注解 @ConditionalOnClass依赖ObjectMapper

查看ObjectMapper源码:

  1. public ObjectMapper registerModule(Module module) {
  2. this._assertNotNull("module", module);
  3. String name = module.getModuleName();
  4. if(name == null) {
  5. throw new IllegalArgumentException("Module without defined name");
  6. } else {
  7. Version version = module.version();
  8. if(version == null) {
  9. throw new IllegalArgumentException("Module without defined version");
  10. } else {
  11. ...
  12. module.setupModule(new SetupContext() {
  13. ...
  14. //反序列化
  15. public void addDeserializers(Deserializers d) {
  16. DeserializerFactory df = ObjectMapper.this._deserializationContext._factory.withAdditionalDeserializers(d);
  17. ObjectMapper.this._deserializationContext = ObjectMapper.this._deserializationContext.with(df);
  18. }
  19. ...
  20. //序列化
  21. public void addSerializers(Serializers s) {
  22. ObjectMapper.this._serializerFactory = ObjectMapper.this._serializerFactory.withAdditionalSerializers(s);
  23. }
  24. ...
  25. });
  26. return this;
  27. }
  28. }
  29. }

由源码可知,ObjectMapper类在此处定义了时间序列化相关配置,查看Module实现类JavaTimeModule

  1. public JavaTimeModule() {
  2. super(PackageVersion.VERSION);
  3. ...
  4. this.addDeserializer(LocalDateTime.class, LocalDateTimeDeserializer.INSTANCE);
  5. this.addDeserializer(LocalDate.class, LocalDateDeserializer.INSTANCE);
  6. this.addDeserializer(LocalTime.class, LocalTimeDeserializer.INSTANCE);
  7. ...
  8. this.addSerializer(LocalDateTime.class, LocalDateTimeSerializer.INSTANCE);
  9. this.addSerializer(LocalDate.class, LocalDateSerializer.INSTANCE);
  10. this.addSerializer(LocalTime.class, LocalTimeSerializer.INSTANCE);
  11. ...
  12. this.addKeyDeserializer(LocalDateTime.class, LocalDateTimeKeyDeserializer.INSTANCE);
  13. this.addKeyDeserializer(LocalDate.class, LocalDateKeyDeserializer.INSTANCE);
  14. this.addKeyDeserializer(LocalTime.class, LocalTimeKeyDeserializer.INSTANCE);
  15. ...
  16. }

JavaTimeModule设置了LocalDateTime,LocalDate,LocalTime的默认的序列化和反序列的实现。

springboot提供了自定义ObjectMapper

  1. /**
  2. * 更改jackson默认配置
  3. * 支持 Date和jdk8的时间操作类
  4. * 配置时间格式化的全局操作,允许配置优先级更高的注解@JsonFormat 当配置@JsonFormat注解时以@JsonFormat配置为主
  5. */
  6. @Bean
  7. public ObjectMapper objectMapper() {
  8. ObjectMapper objectMapper = new ObjectMapper();
  9. // 对于空的对象转json的时候不抛出错误
  10. objectMapper.disable(SerializationFeature.FAIL_ON_EMPTY_BEANS);
  11. // 禁用遇到未知属性抛出异常
  12. objectMapper.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);
  13. // 序列化BigDecimal时不使用科学计数法输出
  14. objectMapper.configure(JsonGenerator.Feature.WRITE_BIGDECIMAL_AS_PLAIN, true);
  15. //null的属性不序列化
  16. objectMapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);
  17. // 日期和时间格式化
  18. JavaTimeModule javaTimeModule = new JavaTimeModule();
  19. javaTimeModule.addSerializer(LocalDateTime.class, new LocalDateTimeSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
  20. javaTimeModule.addSerializer(LocalDate.class, new LocalDateSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd")));
  21. javaTimeModule.addSerializer(LocalTime.class, new LocalTimeSerializer(DateTimeFormatter.ofPattern("HH:mm:ss")));
  22. javaTimeModule.addDeserializer(LocalDateTime.class, new LocalDateTimeDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
  23. javaTimeModule.addDeserializer(LocalDate.class, new LocalDateDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd")));
  24. javaTimeModule.addDeserializer(LocalTime.class, new LocalTimeDeserializer(DateTimeFormatter.ofPattern("HH:mm:ss")));
  25. objectMapper.registerModule(javaTimeModule);
  26. return objectMapper;
  27. }

备注:虽说配置了自定义的ObjectMapper,但依旧只是支持LocalDateTime,LocalDate,LocalTime类相关的配置,若系统内部还是采用Date类型,只需在配置文件中添加

spring.jackson.date-formate=yyyy-MM-dd HH:mm:ss

若需要支持LocalDateTime,LocalDate,LocalTime自定义配置,一定不能使用@EnableWebMvc注解。否则自定义配置ObjectMapper会失效。

  1. {
  2. "id": 5,
  3. "name": null,
  4. "age": null,
  5. "jsonStr": null,
  6. "ct": [
  7. 2020,
  8. 8,
  9. 4,
  10. 14,
  11. 56,
  12. 54,
  13. 971000000
  14. ]
  15. }

自此常用类型的时间在web项目中有服务器返回给前端的的时间格式化可按照自定义格式化处理.

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/凡人多烦事01/article/detail/84633
推荐阅读
相关标签
  

闽ICP备14008679号