diff --git a/src/main/java/org/springframework/data/jpa/provider/HibernateUtils.java b/src/main/java/org/springframework/data/jpa/provider/HibernateUtils.java index d8baf0d48..1b8124bac 100644 --- a/src/main/java/org/springframework/data/jpa/provider/HibernateUtils.java +++ b/src/main/java/org/springframework/data/jpa/provider/HibernateUtils.java @@ -1,5 +1,5 @@ /* - * Copyright 2016 the original author or authors. + * Copyright 2016-2017 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. @@ -20,6 +20,7 @@ import java.util.Arrays; import java.util.List; import org.hibernate.Query; +import org.springframework.data.util.Version; import org.springframework.util.ClassUtils; import org.springframework.util.ReflectionUtils; @@ -39,6 +40,7 @@ public abstract class HibernateUtils { private static final Class HIBERNATE_QUERY_INTERFACE; private static final Method QUERY_STRING_METHOD; + private static final Version HIBERNATE_VERSION; private HibernateUtils() {} @@ -66,6 +68,10 @@ public abstract class HibernateUtils { HIBERNATE_QUERY_INTERFACE = queryInterface == null ? type : queryInterface; QUERY_STRING_METHOD = HIBERNATE_QUERY_INTERFACE == null ? null : ReflectionUtils.findMethod(HIBERNATE_QUERY_INTERFACE, "getQueryString"); + + String versionSource = org.hibernate.Version.getVersionString(); + + HIBERNATE_VERSION = Version.parse(versionSource.substring(0, versionSource.lastIndexOf('.'))); } /** @@ -87,4 +93,14 @@ public abstract class HibernateUtils { return ((Query) ReflectionUtils.invokeMethod(GET_HIBERNATE_QUERY, query)).getQueryString(); } + + /** + * Returns whether the currently used version of Hibernate is equal to or newer than the given one. + * + * @param version must not be {@literal null}. + * @return + */ + public static boolean isVersionOrBetter(Version version) { + return HIBERNATE_VERSION.isGreaterThanOrEqualTo(version); + } } diff --git a/src/main/java/org/springframework/data/jpa/repository/query/NativeJpaQuery.java b/src/main/java/org/springframework/data/jpa/repository/query/NativeJpaQuery.java index d025d4a0d..4ed902638 100644 --- a/src/main/java/org/springframework/data/jpa/repository/query/NativeJpaQuery.java +++ b/src/main/java/org/springframework/data/jpa/repository/query/NativeJpaQuery.java @@ -1,5 +1,5 @@ /* - * Copyright 2013-2016 the original author or authors. + * Copyright 2013-2017 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. @@ -19,11 +19,13 @@ import javax.persistence.EntityManager; import javax.persistence.Query; import javax.persistence.Tuple; +import org.springframework.data.jpa.provider.HibernateUtils; import org.springframework.data.repository.query.EvaluationContextProvider; import org.springframework.data.repository.query.Parameters; import org.springframework.data.repository.query.RepositoryQuery; import org.springframework.data.repository.query.ResultProcessor; import org.springframework.data.repository.query.ReturnedType; +import org.springframework.data.util.Version; import org.springframework.expression.spel.standard.SpelExpressionParser; /** @@ -36,6 +38,8 @@ import org.springframework.expression.spel.standard.SpelExpressionParser; */ final class NativeJpaQuery extends AbstractStringBasedJpaQuery { + private static final Version HIBERNATE_VERSION_SUPPORTING_TUPLES = new Version(5, 2, 11); + private final Class resultType; /** @@ -88,7 +92,8 @@ final class NativeJpaQuery extends AbstractStringBasedJpaQuery { return result; } - return returnedType.isProjecting() && !getMetamodel().isJpaManaged(returnedType.getReturnedType()) ? Tuple.class + return returnedType.isProjecting() && !getMetamodel().isJpaManaged(returnedType.getReturnedType()) // + ? HibernateUtils.isVersionOrBetter(HIBERNATE_VERSION_SUPPORTING_TUPLES) ? Tuple.class : null // : result; } } diff --git a/src/test/java/org/springframework/data/jpa/provider/HibernateUtilsUnitTests.java b/src/test/java/org/springframework/data/jpa/provider/HibernateUtilsUnitTests.java new file mode 100644 index 000000000..3f07a99fe --- /dev/null +++ b/src/test/java/org/springframework/data/jpa/provider/HibernateUtilsUnitTests.java @@ -0,0 +1,37 @@ +/* + * Copyright 2017 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. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.springframework.data.jpa.provider; + +import static org.hamcrest.CoreMatchers.*; +import static org.junit.Assert.*; + +import org.junit.Test; +import org.springframework.data.util.Version; + +/** + * Unit tests for {@link HibernateUtils}. + * + * @author Oliver Gierke + */ +public class HibernateUtilsUnitTests { + + static final Version HIBERNATE_BASELINE = new Version(3, 6, 10); + + @Test + public void looksUpHibernateVersion() { + assertThat(HibernateUtils.isVersionOrBetter(HIBERNATE_BASELINE), is(true)); + } +}