如何在Spring MVC(JPA)中将实体对象列表转换为页面对象?

76

我有一个实体的List。 使用Spring MVC 4和Spring Data JPA,如何将其转换为Page对象?

7个回答

135

有一个Page的实现

final Page<Something> page = new PageImpl<>(theListOfSomething);

11
它不会将它们分成页面,而是返回所有项目在一页中。 - Dhiresh Budhiraja
它会出现错误。 - Sayan Dasgupta

64

还有一个构造函数

Page<Something> page = new PageImpl<>(listOfsomething, pageable, listOfsomething.size());

10
以下是翻译的结果:如何创建“可分页”对象:Pageable pageable = PageRequest.of(pageNumber, size); ,请注意pageNumber是“从零开始”的,而且PageablePageRequest都需要从 org.springframework.data.domain 中导入。更多信息请查看 可分页文档 - Aleksandar
@Mehraj Malik,我的代码在这个问题上无法工作... https://stackoverflow.com/questions/62485592/pageable-in-spring-for-paging-on-listobject-is-not-working - dhS

8

我认为你还需要获取正确的页面内容。


PageRequest pageRequest = PageRequest.of(offset, limit);

List<Product> products = getProducts();

int total = products.size();
int start = toIntExact(pageRequest.getOffset());
int end = Math.min((start + pageRequest.getPageSize()), total);

List<Product> output = new ArrayList<>();

if (start <= end) {
    output = products.subList(start, end);
}

return new PageImpl<>(
    output,
    pageRequest,
    total
);

3
通常情况下,控制器应该接收一个Pageable对象作为参数。这个Pageable对象包含了页码、页面大小和排序信息。
然后,您可以使用排序查询所有实体,并生成Page对象:
List<Entity> allList = jpaRepository.findAll(pageable.getSort());

List<Entity> pageList = allList.stream()
    .skip(pageable.getOffset())
    .limit(pageable.getPageSize())
    .collect(Collectors.toList());

return new PageImpl<>(pageList, pageable, allList.size());


1
你可以使用 pageable.getOffset() 进行跳过,不需要进行乘法运算。 - CptWasp
感谢@CptWasp,已应用于答案。 - zhezha

2
你可以将列表传递到函数中,使其成为可分页的对象。如果子列表的起始值小于列表大小,则返回空内容。
  public Page<?> toPage(List<?> list, Pageable pageable) {
        int start = (int) pageable.getOffset();
        int end = Math.min((start + pageable.getPageSize()), list.size());
        if(start > list.size())
            return new PageImpl<>(new ArrayList<>(), pageable, list.size());
        return new PageImpl<>(list.subList(start, end), pageable, list.size());
    }

1
上述答案都假设列表是您想要返回的内容。以下是在包含记录的列表上执行分页的方法。
//pageNum starts with 1
//size: page size
//totalRecords, total records
Page<Record> myMethod(int pageNum, int size, List<MyRecord> totalRecords){
    if(pageNum<1){
        pageNum = 1;
    }
    if(size < 1){
        size = 10;
    }
    //spring page starts with 0
    Pageable pageable = new PageRequest(pageNum-1, size);
    //when pageNum * size is too big(bigger than list.size()), totalRecords.subList() will throw a exception, we need to fix this
    if(pageable.getOffset() > list.size()){
            pageable = new PageRequest(0, size);
    }
    List<MyRecord> pageRecords = totalRecords.subList(pageable.getOffset(), Math.min(pageable.getOffset() + pageable.getPageSize(), totalRecords.size()));
    
    Page springPage = new PageImpl<>(pageRecords, pageable, totalRecords.size());
    return springPage;
}

0
public static <T> PageData buildCustomPagedData(List<T> data, Pageable pageable) {
    List<T> model = new ArrayList<>();
    int start = VALUE_ZERO;
    if (!Objects.equals(pageable.getPageNumber(), FIRST_INDEX)) {
        start = (pageable.getPageNumber() * pageable.getPageSize());
    }
    for (int i = start; i < start + pageable.getPageSize(); i++) {
        if (i < data.size()) {
            model.add(data.get(i));
        } else {
            break;
        }
    }
    return PageData.builder()
            .model(model)
            .totalElements(data.size())
            .currentPage(pageable.getPageNumber() + INT_ONE)
            .totalPages((data.size() / pageable.getPageSize()) + INT_ONE)
            .build();
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接