Skip to content

Commit 8490417

Browse files
committed
Support binding to generic Object constructor arg
Closes gh-447
1 parent dfed05a commit 8490417

File tree

2 files changed

+56
-18
lines changed

2 files changed

+56
-18
lines changed

spring-graphql/src/main/java/org/springframework/graphql/data/GraphQlArgumentBinder.java

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -248,7 +248,7 @@ private Object createValue(
248248
Object target;
249249
Constructor<?> ctor = BeanUtils.getResolvableConstructor(targetType);
250250

251-
// Default constructor with data binding
251+
// Default constructor + data binding via properties
252252

253253
if (ctor.getParameterCount() == 0) {
254254
target = BeanUtils.instantiateClass(ctor);
@@ -284,6 +284,9 @@ private Object createValue(
284284
if (rawValue == null && methodParam.isOptional()) {
285285
args[i] = (paramTypes[i] == Optional.class ? Optional.empty() : null);
286286
}
287+
else if (paramTypes[i] == Object.class) {
288+
args[i] = rawValue;
289+
}
287290
else if (isApproximableCollectionType(rawValue)) {
288291
ResolvableType elementType = ResolvableType.forMethodParameter(methodParam);
289292
args[i] = createCollection((Collection<Object>) rawValue, elementType, bindingResult, segments);

spring-graphql/src/test/java/org/springframework/graphql/data/GraphQlArgumentBinderTests.java

Lines changed: 52 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -280,6 +280,21 @@ void primaryConstructorBindingErrorWithNestedBeanList() {
280280
});
281281
}
282282

283+
@Test // gh-447
284+
@SuppressWarnings("unchecked")
285+
void primaryConstructorWithGenericObject() throws Exception {
286+
287+
Object result = this.binder.bind(
288+
environment("{\"key\":{\"value\":[{\"name\":\"first\"},{\"name\":\"second\"}]}}"), "key",
289+
ResolvableType.forClass(ObjectHolder.class));
290+
291+
assertThat(result).isNotNull().isInstanceOf(ObjectHolder.class);
292+
List<Map<Object, Object>> list = (List<Map<Object, Object>>) ((ObjectHolder) result).getValue();
293+
assertThat(list).hasSize(2).containsExactly(
294+
Collections.singletonMap("name", "first"),
295+
Collections.singletonMap("name", "second"));
296+
}
297+
283298
@Test // gh-410
284299
@SuppressWarnings("unchecked")
285300
void coercionWithSingletonList() throws Exception {
@@ -332,6 +347,7 @@ private DataFetchingEnvironment environment(String jsonPayload) throws JsonProce
332347
}
333348

334349

350+
@SuppressWarnings("unused")
335351
static class SimpleBean {
336352

337353
private String name;
@@ -434,6 +450,7 @@ public Optional<Item> getItem() {
434450
}
435451

436452

453+
@SuppressWarnings("unused")
437454
static class NoPrimaryConstructorBean {
438455

439456
NoPrimaryConstructorBean(String name) {
@@ -444,6 +461,7 @@ static class NoPrimaryConstructorBean {
444461
}
445462

446463

464+
@SuppressWarnings("unused")
447465
static class ItemListHolder {
448466

449467
private List<Item> items;
@@ -458,6 +476,40 @@ public void setItems(List<Item> items) {
458476
}
459477

460478

479+
@SuppressWarnings("unused")
480+
static class ItemSetHolder {
481+
482+
private Set<Item> items;
483+
484+
public ItemSetHolder(Set<Item> items) {
485+
this.items = items;
486+
}
487+
488+
public Set<Item> getItems() {
489+
return items;
490+
}
491+
492+
public void setItems(Set<Item> items) {
493+
this.items = items;
494+
}
495+
}
496+
497+
498+
static class ObjectHolder {
499+
500+
private final Object value;
501+
502+
ObjectHolder(Object value) {
503+
this.value = value;
504+
}
505+
506+
public Object getValue() {
507+
return value;
508+
}
509+
}
510+
511+
512+
@SuppressWarnings("unused")
461513
static class Item {
462514

463515
private String name;
@@ -494,21 +546,4 @@ public int hashCode() {
494546
}
495547
}
496548

497-
static class ItemSetHolder {
498-
499-
private Set<Item> items;
500-
501-
public ItemSetHolder(Set<Item> items) {
502-
this.items = items;
503-
}
504-
505-
public Set<Item> getItems() {
506-
return items;
507-
}
508-
509-
public void setItems(Set<Item> items) {
510-
this.items = items;
511-
}
512-
}
513-
514549
}

0 commit comments

Comments
 (0)