diff --git a/pom.xml b/pom.xml index dd336ca646..d05c9750ef 100755 --- a/pom.xml +++ b/pom.xml @@ -5,7 +5,7 @@ org.springframework.data spring-data-jpa-parent - 3.3.0-SNAPSHOT + 3.3.x-3409-SNAPSHOT pom Spring Data JPA Parent @@ -41,7 +41,7 @@ 4.8 8.0.33 42.6.0 - 3.3.0-SNAPSHOT + 3.3.x-3070-SNAPSHOT 0.10.3 org.hibernate diff --git a/spring-data-envers/pom.xml b/spring-data-envers/pom.xml index 470678d048..197a2a37cc 100755 --- a/spring-data-envers/pom.xml +++ b/spring-data-envers/pom.xml @@ -5,12 +5,12 @@ org.springframework.data spring-data-envers - 3.3.0-SNAPSHOT + 3.3.x-3409-SNAPSHOT org.springframework.data spring-data-jpa-parent - 3.3.0-SNAPSHOT + 3.3.x-3409-SNAPSHOT ../pom.xml diff --git a/spring-data-jpa-distribution/pom.xml b/spring-data-jpa-distribution/pom.xml index 6bd074181c..bff325f01c 100644 --- a/spring-data-jpa-distribution/pom.xml +++ b/spring-data-jpa-distribution/pom.xml @@ -14,7 +14,7 @@ org.springframework.data spring-data-jpa-parent - 3.3.0-SNAPSHOT + 3.3.x-3409-SNAPSHOT ../pom.xml diff --git a/spring-data-jpa/pom.xml b/spring-data-jpa/pom.xml index 67ad4cabb2..bb4a75b0a9 100644 --- a/spring-data-jpa/pom.xml +++ b/spring-data-jpa/pom.xml @@ -6,7 +6,7 @@ org.springframework.data spring-data-jpa - 3.3.0-SNAPSHOT + 3.3.x-3409-SNAPSHOT Spring Data JPA Spring Data module for JPA repositories. @@ -15,7 +15,7 @@ org.springframework.data spring-data-jpa-parent - 3.3.0-SNAPSHOT + 3.3.x-3409-SNAPSHOT ../pom.xml diff --git a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/PartTreeJpaQuery.java b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/PartTreeJpaQuery.java index 479dc4b52e..3b799258dc 100644 --- a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/PartTreeJpaQuery.java +++ b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/PartTreeJpaQuery.java @@ -259,8 +259,8 @@ public Query createQuery(JpaParametersParameterAccessor accessor) { @SuppressWarnings("ConstantConditions") private Query restrictMaxResultsIfNecessary(Query query, @Nullable ScrollPosition scrollPosition) { - if (scrollPosition instanceof OffsetScrollPosition offset) { - query.setFirstResult(Math.toIntExact(offset.getOffset())); + if (scrollPosition instanceof OffsetScrollPosition offset && !offset.isInitial()) { + query.setFirstResult(Math.toIntExact(offset.getOffset()) + 1); } if (tree.isLimiting()) { diff --git a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/ScrollDelegate.java b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/ScrollDelegate.java index 90c055578d..d529b73f7d 100644 --- a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/ScrollDelegate.java +++ b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/query/ScrollDelegate.java @@ -71,7 +71,7 @@ public Window scroll(Query query, Sort sort, ScrollPosition scrollPosition) { } if (scrollPosition instanceof OffsetScrollPosition offset) { - return createWindow(result, limit, OffsetScrollPosition.positionFunction(offset.getOffset())); + return createWindow(result, limit, OffsetScrollPosition.positionFunction(offset.isInitial() ? 0 : offset.getOffset())); } throw new UnsupportedOperationException("ScrollPosition " + scrollPosition + " not supported"); diff --git a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/QuerydslJpaPredicateExecutor.java b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/QuerydslJpaPredicateExecutor.java index 946dfb23fb..606d56631e 100644 --- a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/QuerydslJpaPredicateExecutor.java +++ b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/QuerydslJpaPredicateExecutor.java @@ -196,7 +196,9 @@ public R findBy(Predicate predicate, Function) querydsl.applySorting(sort, select); if (scrollPosition instanceof OffsetScrollPosition offset) { - select.offset(offset.getOffset()); + if(!offset.isInitial()) { + select.offset(offset.getOffset() + 1); + } } return select.createQuery(); diff --git a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/SimpleJpaRepository.java b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/SimpleJpaRepository.java index 31abc19187..879e683865 100644 --- a/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/SimpleJpaRepository.java +++ b/spring-data-jpa/src/main/java/org/springframework/data/jpa/repository/support/SimpleJpaRepository.java @@ -512,7 +512,9 @@ private R doFindBy(Specification spec, Class domainClass, TypedQuery query = getQuery(specToUse, domainClass, sort); if (scrollPosition instanceof OffsetScrollPosition offset) { - query.setFirstResult(Math.toIntExact(offset.getOffset())); + if(!offset.isInitial()) { + query.setFirstResult(Math.toIntExact(offset.getOffset()) + 1); + } } return query; diff --git a/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryFinderTests.java b/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryFinderTests.java index bea13c14ad..6a8c06789d 100644 --- a/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryFinderTests.java +++ b/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryFinderTests.java @@ -226,16 +226,16 @@ void executesQueryToSliceWithUnpaged() { assertThat(slice.hasNext()).isFalse(); } - @Test // DATAJPA-94 + @Test // GH-3077, GH-3409 void executesQueryWithLimitAndScrollPosition() { Window first = userRepository.findByLastnameOrderByFirstname(Limit.of(1), // - ScrollPosition.offset(), // + ScrollPosition.offset(), // initial position no offset "Matthews" // ); Window next = userRepository.findByLastnameOrderByFirstname(Limit.of(1), // - ScrollPosition.offset(1), // + ScrollPosition.offset(0), // first position, offset = 1 "Matthews" // ); @@ -243,6 +243,17 @@ void executesQueryWithLimitAndScrollPosition() { assertThat(next).containsExactly(oliver); } + @Test // GH-3409 + void executesWindowQueryWithPageable() { + + Window first = userRepository.findByLastnameOrderByFirstname("Matthews", PageRequest.of(0,1)); + + Window next = userRepository.findByLastnameOrderByFirstname("Matthews", PageRequest.of(1,1)); + + assertThat(first).containsExactly(dave); + assertThat(next).containsExactly(oliver); + } + @Test // GH-3077 void shouldProjectWithKeysetScrolling() { diff --git a/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryTests.java b/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryTests.java index 4b802f9773..6f70724709 100644 --- a/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryTests.java +++ b/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/UserRepositoryTests.java @@ -1430,7 +1430,7 @@ void scrollByPartTreeKeysetBackward() { assertThat(previousWindow.hasNext()).isFalse(); } - @Test // GH-3015 + @Test // GH-3015, GH-3407 void shouldApplyOffsetScrollPosition() { User jane1 = new User("Jane", "Doe", "jane@doe1.com"); @@ -1441,7 +1441,7 @@ void shouldApplyOffsetScrollPosition() { repository.saveAllAndFlush(Arrays.asList(john1, john2, jane1, jane2)); Window atOffset3 = repository.findByFirstnameStartingWithOrderByFirstnameAscEmailAddressAsc("J", - ScrollPosition.offset(3)); + ScrollPosition.offset(2)); assertThat(atOffset3).containsExactly(john2); } diff --git a/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/sample/UserRepository.java b/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/sample/UserRepository.java index 2e782982aa..0d898449a1 100644 --- a/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/sample/UserRepository.java +++ b/spring-data-jpa/src/test/java/org/springframework/data/jpa/repository/sample/UserRepository.java @@ -197,6 +197,8 @@ Window findTop3ByFirstnameStartingWithOrderByFirstnameAscEmailAddressAsc(S Window findByLastnameOrderByFirstname(Limit limit, ScrollPosition scrollPosition, String lastname); + Window findByLastnameOrderByFirstname(String lastname, Pageable page); + Window findTop1ByLastnameOrderByFirstname(ScrollPosition scrollPosition, String lastname); List findByLastnameIgnoringCaseLike(String lastname);