Java 8日期/时间(JSR-310)类型与Spring Data MongoDB的映射

时间:2014-05-31 16:00:20

标签: java java-8 spring-data spring-data-mongodb java-time

我有一个带有Java 8日期/时间字段的简单文档

@Document
public class Token {
    private Instant createdAt;
    ...
}

我希望坚持使用Spring Data MongoDB 1.5版。但是java.time.Instant类型的字段无法正确反序列化,因为MappingMongoConverter缺少java.time类的转换器。

在Spring 4中,我发现org.springframework.format.datetime.standard.DateTimeConverters具有不同的Converter,包括InstantToLongConverterLongToInstantConverter声明为私有静态类。

如何配置MongoTemplate使用它们将Instant字段映射为长片?

2 个答案:

答案 0 :(得分:14)

我不知道这是否是最好的方法,但是我将Spring 8 MongoDB 1.5.0.RELEASE的Java 8 Date / Time(JSR-310)类型支持添加到这样:

  1. 第一步。添加简单的Spring Converter s

    public class InstantToLongConverter implements Converter<Instant, Long> {
        @Override
        public Long convert(Instant instant) {
            return instant.toEpochMilli();
        }
    }
    
    public class LongToInstantConverter implements Converter<Long, Instant> {
        @Override
        public Instant convert(Long source) {
            return Instant.ofEpochMilli(source);
        }
    }
    
    public class LocalDateToStringConverter implements Converter<LocalDate, String> {
        @Override
        public String convert(LocalDate localDate) {
            return localDate.toString();
        }
    }
    
    public class StringToLocalDateConverter implements Converter<String, LocalDate> {
        @Override
        public LocalDate convert(String source) {
            return LocalDate.parse(source);
        }
    }
    
  2. 第二步。在Converter实施中将这些自定义MappingMongoConverter注册为AbstractMongoConfiguration,如下所示:

    @Configuration
    @EnableMongoRepositories(basePackages = {"my.app.repository"})
    public class MongoConfiguration extends AbstractMongoConfiguration {
    
        ...
    
        @Override
        public CustomConversions customConversions() {
            return new CustomConversions(Arrays.asList(
                    new InstantToLongConverter(), new LongToInstantConverter(),
                    new LocalDateToStringConverter(), new StringToLocalDateConverter()));
        }
    }
    
  3. 现在,您的文档的Instant字段将保留为长字符号,LocalDate字段将保留为字符串。

答案 1 :(得分:3)

@ user882209完美地解释了这一切 自Spring Data MongoDB 1.7以来,添加了对JSR-310的支持 如果应用程序由Spring Boot支持,则每个超过1.2.8的版本都会包含它 在Spring Boot-ed应用程序中,您可以执行以下操作:

@Configuration
public class MongoDbConfig {

    @Autowired
    private MongoDbFactory mongoDbFactory;

    @Bean
    public MongoTemplate mongoTemplate() {
        MappingMongoConverter converter = new MappingMongoConverter(new DefaultDbRefResolver(mongoDbFactory),
            new MongoMappingContext());
        converter.setCustomConversions(new CustomConversions(Arrays.asList(...)));

    return new MongoTemplate(mongoDbFactory, converter);
    }
}

以下转换器由 Jsr310Converters 类提供:
DateToLocalDateTimeConverter - LocalDateTimeToDateConverter DateToLocalDateConverter - LocalDateToDateConverter DateToLocalTimeConverter - LocalTimeToDateConverter DateToInstantConverter - InstantToDateConverter