Skip to content

Fix Regression in generating queries with nested maps with numeric keys #3689

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@
* @author Thomas Darimont
* @author Christoph Strobl
* @author Mark Paluch
* @author David Julia
*/
public class QueryMapper {

Expand Down Expand Up @@ -1367,11 +1368,17 @@ public TypeInformation<?> getTypeHint() {
static class KeyMapper {

private final Iterator<String> iterator;
private int currentIndex;
private String currentPropertyRoot;
private final List<String> pathParts;

public KeyMapper(String key,
MappingContext<? extends MongoPersistentEntity<?>, MongoPersistentProperty> mappingContext) {

this.iterator = Arrays.asList(key.split("\\.")).iterator();
this.pathParts = Arrays.asList(key.split("\\."));
this.currentPropertyRoot = pathParts.get(0);
this.currentIndex = 0;
this.iterator = pathParts.iterator();
this.iterator.next();
}

Expand All @@ -1389,16 +1396,25 @@ protected String mapPropertyName(MongoPersistentProperty property) {
while (inspect) {

String partial = iterator.next();
currentIndex++;

boolean isPositional = isPositionalParameter(partial) && property.isCollectionLike();
boolean isPositional = isPositionalParameter(partial) && property.isCollectionLike() ;
if(property.isMap() && currentPropertyRoot.equals(partial) && iterator.hasNext()){
partial = iterator.next();
currentIndex++;
}

if (isPositional || property.isMap()) {
if (isPositional || property.isMap() && !currentPropertyRoot.equals(partial)) {
mappedName.append(".").append(partial);
}

inspect = isPositional && iterator.hasNext();
}

if(currentIndex + 1 < pathParts.size()) {
currentIndex++;
currentPropertyRoot = pathParts.get(currentIndex);
}
return mappedName.toString();
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@
* @author Thomas Darimont
* @author Christoph Strobl
* @author Mark Paluch
* @author David Julia
*/
public class QueryMapperUnitTests {

Expand Down Expand Up @@ -730,6 +731,28 @@ void mappingShouldRetainNumericMapKey() {
assertThat(document).containsKey("map.1.stringProperty");
}

@Test // GH-3688
void mappingShouldRetainNestedNumericMapKeys() {

Query query = query(where("outerMap.1.map.2.stringProperty").is("ba'alzamon"));

org.bson.Document document = mapper.getMappedObject(query.getQueryObject(),
context.getPersistentEntity(EntityWithIntKeyedMapOfMap.class));

assertThat(document).containsKey("outerMap.1.map.2.stringProperty");
}

@Test // GH-3688
void mappingShouldAllowSettingEntireNestedNumericKeyedMapValue() {

Query query = query(where("outerMap.1.map").is(null)); //newEntityWithComplexValueTypeMap()

org.bson.Document document = mapper.getMappedObject(query.getQueryObject(),
context.getPersistentEntity(EntityWithIntKeyedMapOfMap.class));

assertThat(document).containsKey("outerMap.1.map");
}

@Test // DATAMONGO-1269
void mappingShouldRetainNumericPositionInList() {

Expand Down Expand Up @@ -1467,6 +1490,10 @@ static class EntityWithComplexValueTypeMap {
Map<Integer, SimpleEntityWithoutId> map;
}

static class EntityWithIntKeyedMapOfMap{
Map<Integer, EntityWithComplexValueTypeMap> outerMap;
}

static class EntityWithComplexValueTypeList {
List<SimpleEntityWithoutId> list;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,7 @@
* @author Thomas Darimont
* @author Mark Paluch
* @author Pavel Vodrazka
* @author David Julia
*/
@ExtendWith(MockitoExtension.class)
class UpdateMapperUnitTests {
Expand Down Expand Up @@ -1179,6 +1180,16 @@ void numericKeyInMapOfNestedPath() {
assertThat(mappedUpdate).isEqualTo("{\"$set\": {\"map.601218778970110001827396.value\": \"testing\"}}");
}

@Test // GH-3688
void multipleNumericKeysInNestedPath() {

Update update = new Update().set("intKeyedMap.12345.map.0", "testing");
Document mappedUpdate = mapper.getMappedObject(update.getUpdateObject(),
context.getPersistentEntity(EntityWithIntKeyedMap.class));

assertThat(mappedUpdate).isEqualTo("{\"$set\": {\"intKeyedMap.12345.map.0\": \"testing\"}}");
}

@Test // GH-3566
void mapsObjectClassPropertyFieldInMapValueTypeAsKey() {

Expand Down Expand Up @@ -1425,6 +1436,10 @@ static class EntityWithObjectMap {
Map<Object, NestedDocument> concreteMap;
}

static class EntityWithIntKeyedMap{
Map<Integer, EntityWithObjectMap> intKeyedMap;
}

static class ClassWithEnum {

Allocation allocation;
Expand Down