From 3811ce5873b7c053101425aea432d13892e34e7e Mon Sep 17 00:00:00 2001 From: Oliver Gierke Date: Fri, 23 Sep 2016 14:46:59 +0200 Subject: [PATCH] DATACMNS-917 - Query method execution for Maps now defaults null to an empty Map. QueryExecutionResultHandler now explicitly handles null values for query methods returning Maps by returning an empty Map. This can be the case if a query is supposed to produce a Map (a single result) but doesn't actually yield any results at all. --- .../core/support/QueryExecutionResultHandler.java | 15 +++++++++++---- .../QueryExecutionResultHandlerUnitTests.java | 13 ++++++++++++- 2 files changed, 23 insertions(+), 5 deletions(-) diff --git a/src/main/java/org/springframework/data/repository/core/support/QueryExecutionResultHandler.java b/src/main/java/org/springframework/data/repository/core/support/QueryExecutionResultHandler.java index b1c65a29a..38acd529f 100644 --- a/src/main/java/org/springframework/data/repository/core/support/QueryExecutionResultHandler.java +++ b/src/main/java/org/springframework/data/repository/core/support/QueryExecutionResultHandler.java @@ -15,6 +15,9 @@ */ package org.springframework.data.repository.core.support; +import java.util.Map; + +import org.springframework.core.CollectionFactory; import org.springframework.core.convert.TypeDescriptor; import org.springframework.core.convert.support.DefaultConversionService; import org.springframework.core.convert.support.GenericConversionService; @@ -68,11 +71,15 @@ class QueryExecutionResultHandler { return conversionService.convert(new NullableWrapper(result), expectedReturnType); } - if (result == null) { - return null; + if (result != null) { + return conversionService.canConvert(result.getClass(), expectedReturnType) + ? conversionService.convert(result, expectedReturnType) : result; } - return conversionService.canConvert(result.getClass(), expectedReturnType) ? conversionService.convert(result, - expectedReturnType) : result; + if (Map.class.equals(expectedReturnType)) { + return CollectionFactory.createMap(expectedReturnType, 0); + } + + return null; } } diff --git a/src/test/java/org/springframework/data/repository/core/support/QueryExecutionResultHandlerUnitTests.java b/src/test/java/org/springframework/data/repository/core/support/QueryExecutionResultHandlerUnitTests.java index 773f79377..52c6bb58b 100644 --- a/src/test/java/org/springframework/data/repository/core/support/QueryExecutionResultHandlerUnitTests.java +++ b/src/test/java/org/springframework/data/repository/core/support/QueryExecutionResultHandlerUnitTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2014 the original author or authors. + * Copyright 2014-2016 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -21,6 +21,7 @@ import static org.junit.Assert.*; import java.lang.reflect.Method; import java.util.Collections; import java.util.List; +import java.util.Map; import java.util.Optional; import java.util.Set; @@ -102,6 +103,14 @@ public class QueryExecutionResultHandlerUnitTests { assertThat(optional, is(com.google.common.base.Optional.of(entity))); } + /** + * @see DATACMNS-917 + */ + @Test + public void defaultsNullToEmptyMap() throws Exception { + assertThat(handler.postProcessInvocationResult(null, getTypeDescriptorFor("map")), is(instanceOf(Map.class))); + } + private static TypeDescriptor getTypeDescriptorFor(String methodName) throws Exception { Method method = Sample.class.getMethod(methodName); @@ -117,6 +126,8 @@ public class QueryExecutionResultHandlerUnitTests { Optional jdk8Optional(); com.google.common.base.Optional guavaOptional(); + + Map map(); } static class Entity {}