From 5f9b0f003f5443d76eb1aa719601deb2c4feb99c Mon Sep 17 00:00:00 2001 From: Christoph Strobl Date: Mon, 22 May 2023 10:36:53 +0200 Subject: [PATCH] Fix converter registration when using driver native time codec. This commit prevents converters from being used as writing converter causing asymmetric write/read operations. Closes #4390 Original pull request: #4392 --- .../core/convert/MongoCustomConversions.java | 4 +++ .../data/mongodb/core/MongoTemplateTests.java | 28 +++++++++++++++++-- .../MongoCustomConversionsUnitTests.java | 10 +++++++ 3 files changed, 40 insertions(+), 2 deletions(-) diff --git a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/MongoCustomConversions.java b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/MongoCustomConversions.java index 53ab1da4b..2d9b4abf4 100644 --- a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/MongoCustomConversions.java +++ b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/MongoCustomConversions.java @@ -42,6 +42,7 @@ import org.springframework.data.convert.PropertyValueConversions; import org.springframework.data.convert.PropertyValueConverter; import org.springframework.data.convert.PropertyValueConverterFactory; import org.springframework.data.convert.PropertyValueConverterRegistrar; +import org.springframework.data.convert.ReadingConverter; import org.springframework.data.convert.SimplePropertyValueConversions; import org.springframework.data.convert.WritingConverter; import org.springframework.data.mapping.model.SimpleTypeHolder; @@ -370,6 +371,7 @@ public class MongoCustomConversions extends org.springframework.data.convert.Cus }, this.propertyValueConversions); } + @ReadingConverter private enum DateToUtcLocalDateTimeConverter implements Converter { INSTANCE; @@ -379,6 +381,7 @@ public class MongoCustomConversions extends org.springframework.data.convert.Cus } } + @ReadingConverter private enum DateToUtcLocalTimeConverter implements Converter { INSTANCE; @@ -388,6 +391,7 @@ public class MongoCustomConversions extends org.springframework.data.convert.Cus } } + @ReadingConverter private enum DateToUtcLocalDateConverter implements Converter { INSTANCE; diff --git a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateTests.java b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateTests.java index 72ea28aeb..a8b108566 100644 --- a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateTests.java +++ b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateTests.java @@ -39,13 +39,11 @@ import java.util.concurrent.atomic.AtomicReference; import java.util.stream.Collectors; import java.util.stream.IntStream; -import org.bson.Document; import org.bson.types.ObjectId; import org.joda.time.DateTime; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.Test; import org.junit.jupiter.api.extension.ExtendWith; - import org.springframework.context.ConfigurableApplicationContext; import org.springframework.context.support.GenericApplicationContext; import org.springframework.core.convert.converter.Converter; @@ -67,6 +65,8 @@ import org.springframework.data.mongodb.InvalidMongoDbApiUsageException; import org.springframework.data.mongodb.MongoDatabaseFactory; import org.springframework.data.mongodb.core.BulkOperations.BulkMode; import org.springframework.data.mongodb.core.convert.LazyLoadingProxy; +import org.springframework.data.mongodb.core.convert.MongoCustomConversions; +import org.springframework.data.mongodb.core.convert.MongoCustomConversions.MongoConverterConfigurationAdapter; import org.springframework.data.mongodb.core.geo.GeoJsonPoint; import org.springframework.data.mongodb.core.index.Index; import org.springframework.data.mongodb.core.index.IndexField; @@ -1787,6 +1787,30 @@ public class MongoTemplateTests { assertThat(result.get(0).date).isNotNull(); } + @Test // GH-4390 + void nativeDriverDateTimeCodecShouldBeApplied/*when configured*/() { + + MongoTestTemplate ops = new MongoTestTemplate(cfg -> { + cfg.configureConversion(conversion -> { + conversion.customConversions( + MongoCustomConversions.create(MongoConverterConfigurationAdapter::useNativeDriverJavaTimeCodecs)); + }); + }); + + TypeWithDate source = new TypeWithDate(); + source.id = "id-1"; + source.date = Date.from(Instant.now()); + + ops.save(source); + + Object dbDate = ops.execute(TypeWithDate.class, + collection -> collection.find(new org.bson.Document("_id", source.id)).first().get("date")); + + TypeWithDate target = ops.findOne(query(where("date").is(source.date)), TypeWithDate.class); + + assertThat(target.date).isEqualTo(source.date).isEqualTo(dbDate); + } + @Test // DATAMONGO-540 public void findOneAfterUpsertForNonExistingObjectReturnsTheInsertedObject() { diff --git a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/MongoCustomConversionsUnitTests.java b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/MongoCustomConversionsUnitTests.java index 84924f354..ca13bc791 100644 --- a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/MongoCustomConversionsUnitTests.java +++ b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/MongoCustomConversionsUnitTests.java @@ -64,6 +64,16 @@ class MongoCustomConversionsUnitTests { assertThat(conversions.getPropertyValueConversions().hasValueConverter(persistentProperty)).isTrue(); } + @Test // GH-4390 + void doesNotReturnConverterForNativeTimeTimeIfUsingDriverCodec() { + + MongoCustomConversions conversions = MongoCustomConversions.create(config -> { + config.useNativeDriverJavaTimeCodecs(); + }); + + assertThat(conversions.getCustomWriteTarget(Date.class)).isEmpty(); + } + static class DateToZonedDateTimeConverter implements Converter { @Override