SpringJPA不能同时使用top和pageable

368yc8dk  于 2021-06-30  发布在  Java
关注(0)|答案(4)|浏览(276)

我有一个带有方法名查询的存储库来返回前3个实体,例如。

@Repository
public interface MyEntityRepository extends PagingAndSortingRepository<MyEntity, Integer> {
    Page<MyEntity> findTop3By(Pageable pageable);
}

该方法还支持 Pageable 给结果分页。但是,返回的结果不符合可分页大小,并且非常混乱。e、 g.当共有5个实体时

myEntityRepository.findTop3By(PageRequest.of(0, 9))
// page 0 and size 9, got top 3 entities
// (good)

myEntityRepository.findTop3By(PageRequest.of(0, 4))
// page 0 and size 4, still got top 3 entities
// (good)

myEntityRepository.findTop3By(PageRequest.of(0, 3))
// page 0 and size 3, still got top 3 entities, however, returned TotalElements is 5
// (partial, expected TotalElements is 3 so that there is no next page)

myEntityRepository.findTop3By(PageRequest.of(1, 3))
// page 1 and size 3, got the 4th and 5th entities, returned TotalElements is 5 
// (wrong, expected no entities)

myEntityRepository.findTop3By(PageRequest.of(0, 2))
// page 0 and size 2, still got top 3 entities, returned TotalElements is 5
// (wrong, does not respect the page size, expected only the 1st and 2nd entities)

myEntityRepository.findTop3By(PageRequest.of(1, 2))
// page 1 and size 2, got 3rd, 4th and 5th entities, returned TotalElements is 5
// (wrong, expected only the 3rd entity)

如何解决此问题以获得预期结果?

rm5edbpk

rm5edbpk1#

如果我的理解是正确的,那么您需要对存储库查询进行分页,并对响应进行排序。在这种情况下,您的存储库应该扩展 PagingAndSortingRepository<MyEntity, Integer> ```
public interface MyEntityRepository extends
PagingAndSortingRepository<MyEntity, Integer> {

List<MyEntity> findAllByColumnName(String ColumnName, 
                                   Pageable pageable);

}

然后你必须创建一个 `pageRequest` .

for(int pageCounter= 0; pageCounter < 100; ++i)
Pageable PageRequestwithTopthree =
PageRequest.of(pageCounter, 3, sort.by("column_name").descending());
}

编辑
如果页面大小不同,请在pagerequest中进行更改

Pageable PageRequestwithTopthree =
PageRequest.of(pageCounter, pageSize,
sort.by("column_name").descending());

isr3a4wc

isr3a4wc2#

类pagerequest的构造函数如下

protected PageRequest(int page, int size, Sort sort)

我们倾向于通过一个'排序'的一些规则,你想订购。

sq1bmfud

sq1bmfud3#

您应该配置 Pageable 以这种方式在服务层上

public Page<MyEntity> getTop3Page(int page, int size) {
    int topElementsNumber = 3;
    if(size > topElementsNumber) {
        size = topElementsNumber;
    }  

    List<MyEntity> content = getPageContent(page, size, topElementsNumber);
    return new PageImpl<>(content, pageable, topElementsNumber);
}

private List<MyEntity> getPageContent(int page, int size, int topElementsNumber) {
    int lastPage = getLastPage(size, topElementsNumber);

    Pageable pageable = PageRequest.of(page, size);
    if(page > lastPage) {
        return Collections.emptyList();
    }

    Page<MyEntity> page = repository.findAll(pageable);

    int pageLastElementNumber = (page + 1) * size;
    if(pageLastElementNumber > topElementsNumber) {
        int sublistSize = size - (pageLastElementNumber - topElementsNumber);
        return page.getContent().subList(0, sublistSize);
    } 

    return page.getContent();
}

private int getLastPage(int size, int topElementsNumber) {
    int lastPage = (topElementsNumber / size) - 1;
    if(topElementsNumber % size > 0) {
        lastPage++;
    }

    return lastPage;
}
nnvyjq4y

nnvyjq4y4#

您可以按如下方式定义一个方法(找到所有行,然后分页):

List<Foo> findAllByOrderBySomethingAsc(Pageable pageable)

相关问题