Spring MVC Tutorial

Core Spring MVC

Spring MVC - Annotation

Spring MVC - Form Handling

Spring MVC with JSTL

Spring MVC with REST API

Spring MVC with Database

Spring MVC - Pagination with Example

Pagination is a technique to display a large number of records in manageable sets or pages. In web applications, pagination helps in enhancing the user experience by presenting data in a structured manner. When combined with Spring MVC, pagination can be achieved in a seamless and efficient way.

Let's walk through the process of implementing pagination in a Spring MVC application using Spring's Page and Pageable interfaces from Spring Data JPA.

1. Dependencies:

Ensure you have the required dependencies in your pom.xml:

<!-- Spring Web MVC -->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-webmvc</artifactId>
    <version>5.x.x.RELEASE</version>
</dependency>

<!-- Spring Data JPA -->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>

<!-- Your database driver here, e.g., H2 -->
<dependency>
    <groupId>com.h2database</groupId>
    <artifactId>h2</artifactId>
</dependency>

2. Repository:

Your repository should extend PagingAndSortingRepository or JpaRepository:

public interface UserRepository extends JpaRepository<User, Long> {
}

3. Controller:

In your controller, use the Pageable parameter to receive pagination information:

@Controller
@RequestMapping("/users")
public class UserController {

    @Autowired
    private UserRepository userRepository;

    @GetMapping
    public String listUsers(@RequestParam(defaultValue = "0") int page, Model model) {
        Page<User> userPage = userRepository.findAll(PageRequest.of(page, 10)); // 10 records per page
        model.addAttribute("data", userPage);
        return "userList";
    }
}

4. View (JSP):

Display the paginated data and pagination controls:

<table>
    <thead>
        <tr>
            <th>ID</th>
            <th>Name</th>
            <!-- Other columns -->
        </tr>
    </thead>
    <tbody>
        <c:forEach items="${data.content}" var="user">
            <tr>
                <td>${user.id}</td>
                <td>${user.name}</td>
                <!-- Other columns -->
            </tr>
        </c:forEach>
    </tbody>
</table>

<!-- Pagination controls -->
<div>
    <c:if test="${data.totalPages > 0}">
        <ul>
            <c:forEach begin="0" end="${data.totalPages-1}" var="pageNum">
                <li><a href="<c:url value='/users?page=${pageNum}' />">${pageNum + 1}</a></li>
            </c:forEach>
        </ul>
    </c:if>
</div>

5. Styling:

You might want to add some CSS for better presentation of the paginated data and the pagination controls.

Notes:

  • The Page object contains metadata about the total number of pages, the total number of elements, the current page number, etc. This is useful for building pagination controls in the view.

  • The Pageable object can be used to specify not just pagination information, but also sorting details.

  • You can customize the default parameters for Pageable (like page, size, and sort) by customizing the PageableHandlerMethodArgumentResolver bean in your configuration.

With this setup, as users navigate between pages, only the data for the current page will be fetched from the database, ensuring efficient resource utilization.

  1. Spring MVC Pagination Example:

    • Description: This is a basic example showcasing how to implement pagination in a Spring MVC application.

    • Code Snippet: (Controller)

      @Controller
      public class ProductController {
      
          @Autowired
          private ProductService productService;
      
          @RequestMapping("/products")
          public String getProducts(Model model, @RequestParam(defaultValue = "0") int page) {
              Page<Product> productPage = productService.getPaginatedProducts(page, 10);
      
              model.addAttribute("productPage", productPage);
      
              return "productList";
          }
      }
      

      (Service)

      @Service
      public class ProductService {
      
          @Autowired
          private ProductRepository productRepository;
      
          public Page<Product> getPaginatedProducts(int page, int size) {
              Pageable pageable = PageRequest.of(page, size);
              return productRepository.findAll(pageable);
          }
      }
      

      (Thymeleaf - productList.html)

      <table>
          <!-- Display product list -->
          <tr th:each="product : ${productPage.content}">
              <td th:text="${product.name}"></td>
              <td th:text="${product.price}"></td>
          </tr>
      </table>
      
      <!-- Display pagination links -->
      <div th:fragment="pagination">
          <ul class="pagination">
              <li th:if="${productPage.hasPrevious()}">
                  <a th:href="@{/products(page=${productPage.previousPageable().pageNumber})}">&laquo; Previous</a>
              </li>
              <li th:each="i : ${#numbers.sequence(0, productPage.totalPages - 1)}" th:class="${productPage.number == i} ? 'active'">
                  <a th:href="@{/products(page=${i})}" th:text="${i + 1}"></a>
              </li>
              <li th:if="${productPage.hasNext()}">
                  <a th:href="@{/products(page=${productPage.nextPageable().pageNumber})}">Next &raquo;</a>
              </li>
          </ul>
      </div>
      
  2. Client-Side Pagination with Spring MVC:

    • Description: This example showcases client-side pagination in a Spring MVC application.

    • Code Snippet: (Controller and Service are similar to the first example)

      (Thymeleaf - productList.html)

      <table id="productTable">
          <!-- Display product list -->
          <tr th:each="product : ${productPage.content}">
              <td th:text="${product.name}"></td>
              <td th:text="${product.price}"></td>
          </tr>
      </table>
      
      <!-- Include the DataTables JavaScript library -->
      <script src="https://cdn.datatables.net/1.10.24/js/jquery.dataTables.min.js"></script>
      
      <!-- Initialize DataTables with pagination -->
      <script>
          $(document).ready(function () {
              $('#productTable').DataTable();
          });
      </script>
      
  3. Paginating Data with Spring Data JPA in Spring MVC:

    • Description: This example demonstrates paginating data using Spring Data JPA in a Spring MVC application.

    • Code Snippet: (Service)

      @Service
      public class ProductService {
      
          @Autowired
          private ProductRepository productRepository;
      
          public Page<Product> getPaginatedProducts(int page, int size) {
              Pageable pageable = PageRequest.of(page, size);
              return productRepository.findAll(pageable);
          }
      }