diff --git a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/QueryMapper.java b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/QueryMapper.java index 5af1f9fe9..fe4d4569d 100644 --- a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/QueryMapper.java +++ b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/QueryMapper.java @@ -373,7 +373,9 @@ public class QueryMapper { if (keyword.isOrOrNor() || (keyword.hasIterableValue() && !keyword.isGeometry())) { Iterable conditions = keyword.getValue(); - List newConditions = conditions instanceof Collection ? new ArrayList<>(((Collection) conditions).size()) : new ArrayList<>(); + List newConditions = conditions instanceof Collection + ? new ArrayList<>(((Collection) conditions).size()) + : new ArrayList<>(); for (Object condition : conditions) { newConditions.add(isDocument(condition) ? getMappedObject((Document) condition, entity) @@ -431,8 +433,10 @@ public class QueryMapper { Object value = applyFieldTargetTypeHintToValue(documentField, sourceValue); - if(documentField.getProperty() != null && converter.getCustomConversions().hasValueConverter(documentField.getProperty())) { - return converter.getCustomConversions().getPropertyValueConversions().getValueConverter(documentField.getProperty()) + if (documentField.getProperty() != null + && converter.getCustomConversions().hasValueConverter(documentField.getProperty())) { + return converter.getCustomConversions().getPropertyValueConversions() + .getValueConverter(documentField.getProperty()) .write(value, new MongoConversionContext(documentField.getProperty(), converter)); } @@ -616,7 +620,11 @@ public class QueryMapper { } protected Object convertAssociation(Object source, Field field) { - return convertAssociation(source, field.getProperty()); + Object value = convertAssociation(source, field.getProperty()); + if (value != null && field.isIdField() && field.getFieldType() != value.getClass()) { + return convertId(value, field.getFieldType()); + } + return value; } /** @@ -1042,6 +1050,9 @@ public class QueryMapper { return TypeInformation.OBJECT; } + public Class getFieldType() { + return Object.class; + } } /** @@ -1170,6 +1181,11 @@ public class QueryMapper { return null; } + @Override + public Class getFieldType() { + return property.getFieldType(); + } + @Override public String getMappedKey() { return path == null ? name : path.toDotPath(isAssociation() ? getAssociationConverter() : getPropertyConverter()); diff --git a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/QueryMapperUnitTests.java b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/QueryMapperUnitTests.java index d3b73379b..06f6aec93 100755 --- a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/QueryMapperUnitTests.java +++ b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/convert/QueryMapperUnitTests.java @@ -437,6 +437,31 @@ public class QueryMapperUnitTests { assertThat(mappedQuery).containsEntry("sample", "s1"); } + @Test // GH-4033 + void convertsNestedPathToIdPropertyOfDocumentReferenceCorrectly() { + + Query query = query(where("sample.foo").is("s1")); + org.bson.Document mappedQuery = mapper.getMappedObject(query.getQueryObject(), + context.getPersistentEntity(WithDocumentReference.class)); + + assertThat(mappedQuery).containsEntry("sample", "s1"); + } + + @Test // GH-4033 + void convertsNestedPathToIdPropertyOfDocumentReferenceCorrectlyWhenItShouldBeConvertedToObjectId() { + + ObjectId id = new ObjectId(); + Query query = query(where("sample.foo").is(id.toHexString())); + org.bson.Document mappedQuery = mapper.getMappedObject(query.getQueryObject(), + context.getPersistentEntity(WithDocumentReference.class)); + + assertThat(mappedQuery.get("sample")).satisfies(it -> { + + assertThat(it).isInstanceOf(ObjectId.class); + assertThat(((ObjectId) it).toHexString()).isEqualTo(id.toHexString()); + }); + } + @Test // GH-3853 void convertsListDocumentReferenceOnIdPropertyCorrectly() {