Skip to content

Commit d34d6a9

Browse files
committed
Properly merge non-entity arrays.
Fixes #2325.
1 parent 3ee5660 commit d34d6a9

File tree

2 files changed

+53
-4
lines changed

2 files changed

+53
-4
lines changed

spring-data-rest-webmvc/src/main/java/org/springframework/data/rest/webmvc/json/DomainObjectReader.java

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -267,9 +267,8 @@ <T> T doMerge(ObjectNode root, T target, ObjectMapper mapper) throws Exception {
267267

268268
if (child.isArray()) {
269269

270-
IntFunction<Object> rawValues = index -> readRawCollectionElement(property.getComponentType(), fieldName, index,
271-
root,
272-
mapper);
270+
IntFunction<Object> rawValues = index -> readRawCollectionElement(property.getComponentType(), fieldName,
271+
index, root, mapper);
273272

274273
if (handleArray(child, it, mapper, property.getTypeInformation(), rawValues)) {
275274
i.remove();
@@ -366,7 +365,8 @@ private boolean handleArrayNode(ArrayNode array, Collection<Object> collection,
366365
if (array.isEmpty()
367366
|| collection.isEmpty()
368367
|| ClassUtils.isPrimitiveOrWrapper(componentType.getType())
369-
|| componentType.getType().isEnum()) {
368+
|| componentType.getType().isEnum()
369+
|| entities.getPersistentEntity(componentType.getType()).isEmpty()) {
370370
return false;
371371
}
372372

spring-data-rest-webmvc/src/test/java/org/springframework/data/rest/webmvc/json/DomainObjectReaderUnitTests.java

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,7 @@ void setUp() {
114114
mappingContext.getPersistentEntity(Pear.class);
115115
mappingContext.getPersistentEntity(WithCustomMappedPrimitiveCollection.class);
116116
mappingContext.getPersistentEntity(BugModel.class);
117+
mappingContext.getPersistentEntity(ArrayListHolder.class);
117118
mappingContext.afterPropertiesSet();
118119

119120
this.entities = new PersistentEntities(Collections.singleton(mappingContext));
@@ -705,6 +706,42 @@ void deserializesNewNestedEntitiesCorrectly() throws Exception {
705706
.containsExactly("Foo", "Bar");
706707
}
707708

709+
@Test // #2325
710+
void arraysCanMutateAndAppendDuringMerge() throws Exception {
711+
712+
ObjectMapper mapper = new ObjectMapper();
713+
ArrayHolder target = new ArrayHolder(new String[] { "ancient", "old", "older" });
714+
JsonNode node = mapper.readTree("{ \"array\" : [ \"new\", \"old\", \"newer\", \"bleeding edge\" ] }");
715+
716+
ArrayHolder updated = reader.doMerge((ObjectNode) node, target, mapper);
717+
718+
assertThat(updated.array).containsExactly("new", "old", "newer", "bleeding edge");
719+
}
720+
721+
@Test // #2325
722+
void arraysCanAppendMoreThanOneElementDuringMerge() throws Exception {
723+
724+
ObjectMapper mapper = new ObjectMapper();
725+
ArrayListHolder target = new ArrayListHolder("ancient", "old", "older");
726+
JsonNode node = mapper.readTree("{ \"values\" : [ \"ancient\", \"old\", \"older\", \"new\", \"newer\" ] }");
727+
728+
ArrayListHolder updated = reader.doMerge((ObjectNode) node, target, mapper);
729+
730+
assertThat(updated.values).containsExactly("ancient", "old", "older", "new", "newer");
731+
}
732+
733+
@Test // #2325
734+
void arraysCanRemoveElementsDuringMerge() throws Exception {
735+
736+
ObjectMapper mapper = new ObjectMapper();
737+
ArrayHolder target = new ArrayHolder(new String[] { "ancient", "old", "older" });
738+
JsonNode node = mapper.readTree("{ \"array\" : [ \"ancient\" ] }");
739+
740+
ArrayHolder updated = reader.doMerge((ObjectNode) node, target, mapper);
741+
742+
assertThat(updated.array).containsExactly("ancient");
743+
}
744+
708745
@SuppressWarnings("unchecked")
709746
private static <T> T as(Object source, Class<T> type) {
710747

@@ -997,4 +1034,16 @@ static class NestedModel {
9971034
public String value;
9981035
}
9991036
}
1037+
1038+
static class ArrayListHolder {
1039+
Collection<String> values;
1040+
1041+
ArrayListHolder(String... values) {
1042+
this.values = new ArrayList<>(Arrays.asList(values));
1043+
}
1044+
1045+
public void setValues(Collection<String> values) {
1046+
this.values = values;
1047+
}
1048+
}
10001049
}

0 commit comments

Comments
 (0)