diff --git a/pom.xml b/pom.xml index 5d28c8a5c5..650bb0f084 100644 --- a/pom.xml +++ b/pom.xml @@ -5,7 +5,7 @@ org.springframework.data spring-data-mongodb-parent - 3.3.0-SNAPSHOT + 3.3.0-GH-3805-SNAPSHOT pom Spring Data MongoDB diff --git a/spring-data-mongodb-benchmarks/pom.xml b/spring-data-mongodb-benchmarks/pom.xml index 0033bd11d5..24cf8189e5 100644 --- a/spring-data-mongodb-benchmarks/pom.xml +++ b/spring-data-mongodb-benchmarks/pom.xml @@ -7,7 +7,7 @@ org.springframework.data spring-data-mongodb-parent - 3.3.0-SNAPSHOT + 3.3.0-GH-3805-SNAPSHOT ../pom.xml diff --git a/spring-data-mongodb-distribution/pom.xml b/spring-data-mongodb-distribution/pom.xml index f62c8dc7f4..03b272f4bc 100644 --- a/spring-data-mongodb-distribution/pom.xml +++ b/spring-data-mongodb-distribution/pom.xml @@ -14,7 +14,7 @@ org.springframework.data spring-data-mongodb-parent - 3.3.0-SNAPSHOT + 3.3.0-GH-3805-SNAPSHOT ../pom.xml diff --git a/spring-data-mongodb/pom.xml b/spring-data-mongodb/pom.xml index 1f157e75bc..380fb1d341 100644 --- a/spring-data-mongodb/pom.xml +++ b/spring-data-mongodb/pom.xml @@ -11,7 +11,7 @@ org.springframework.data spring-data-mongodb-parent - 3.3.0-SNAPSHOT + 3.3.0-GH-3805-SNAPSHOT ../pom.xml diff --git a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/ReferenceLookupDelegate.java b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/ReferenceLookupDelegate.java index 3ca730452f..66f2307adc 100644 --- a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/ReferenceLookupDelegate.java +++ b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/core/convert/ReferenceLookupDelegate.java @@ -19,6 +19,7 @@ import java.util.ArrayList; import java.util.Collection; import java.util.Collections; +import java.util.Iterator; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; @@ -119,7 +120,9 @@ private ReferenceCollection computeReferenceContext(MongoPersistentProperty prop // Use the first value as a reference for others in case of collection like if (value instanceof Iterable) { - value = ((Iterable) value).iterator().next(); + + Iterator iterator = ((Iterable) value).iterator(); + value = iterator.hasNext() ? iterator.next() : new Document(); } // handle DBRef value @@ -247,6 +250,10 @@ DocumentReferenceQuery computeFilter(MongoPersistentProperty property, Object va ors.add(decoded); } + if(ors.isEmpty()) { + return new ListDocumentReferenceQuery(new Document("_id", new Document("$exists", false)), sort); + } + return new ListDocumentReferenceQuery(new Document("$or", ors), sort); } diff --git a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateDocumentReferenceTests.java b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateDocumentReferenceTests.java index d6bcc10e49..c523844af6 100644 --- a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateDocumentReferenceTests.java +++ b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/core/MongoTemplateDocumentReferenceTests.java @@ -25,6 +25,7 @@ import lombok.Setter; import lombok.ToString; +import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.LinkedHashMap; @@ -678,6 +679,41 @@ void loadCollectionReferenceWithMissingRefs() { assertThat(result.getSimpleValueRef()).containsExactly(new SimpleObjectRef("ref-2", "me-the-2-referenced-object")); } + @Test // GH-3805 + void loadEmptyCollectionReference() { + + String rootCollectionName = template.getCollectionName(CollectionRefRoot.class); + + // an empty reference array. + Document source = new Document("_id", "id-1").append("value", "v1").append("simplePreinitializedValueRef", + Collections.emptyList()); + + template.execute(db -> { + db.getCollection(rootCollectionName).insertOne(source); + return null; + }); + + CollectionRefRoot result = template.findOne(query(where("id").is("id-1")), CollectionRefRoot.class); + assertThat(result.simplePreinitializedValueRef).isEmpty(); + } + + @Test // GH-3805 + void loadNoExistingCollectionReference() { + + String rootCollectionName = template.getCollectionName(CollectionRefRoot.class); + + // no reference array at all + Document source = new Document("_id", "id-1").append("value", "v1"); + + template.execute(db -> { + db.getCollection(rootCollectionName).insertOne(source); + return null; + }); + + CollectionRefRoot result = template.findOne(query(where("id").is("id-1")), CollectionRefRoot.class); + assertThat(result.simplePreinitializedValueRef).isEmpty(); + } + @Test // GH-3602 void queryForReference() { @@ -1094,6 +1130,9 @@ static class CollectionRefRoot { @DocumentReference(lookup = "{ '_id' : '?#{#target}' }") // List simpleValueRef; + @DocumentReference + List simplePreinitializedValueRef = new ArrayList<>(); + @DocumentReference(lookup = "{ '_id' : '?#{#target}' }", sort = "{ '_id' : -1 } ") // List simpleSortedValueRef;