Spring RestTemplate - consume paginated response API java

RestTemplate in spring is used to consume REST API simplifying the process for the developer. It includes HTTP connection handling and is integrated with Jackson library binding to serialize and deserialize Java objects to/from json objects.

It is easy to integrate external APIs in Java and Android codebases.

This tutorial will not cover creating REST API in java.

How to consume plain json data using RestTemplate

Let’s assume that REST API returns the following json data.

The following data returns an only array, but not pagination data.

[{"id":1,"mobile":"1234","email":test@gmail,"designation":"Manager","department":"Finance "}]

Let’s create a java value object class for storing data from REST APIs

public class EmployeeInfo {
    private String id;
    private String mobile;
    private String designation;
    private String department;
    private String email;

    public String getMobile() {
        return mobile;
    }

    public void setMobile(String mobile) {
        this.mobile = mobile;
    }

    public String getDesignation() {
        return designation;
    }

    public void setDesignation(String designation) {
        this.designation = designation;
    }

    public String getDepartment() {
        return department;
    }

    public void setDepartment(String department) {
        this.department = department;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    public String getId() {
        return id;
    }

    public void setId(String id) {
        this.id = id;
    }
}

And the REST API consumes with a plan.

final String url = "REST API URL";
RestTemplate restTemplate = new RestTemplate();
EmployeeInfo emp = restTemplate.getForObject(url, EmployeeInfo.class);

restTemplate in Spring framework object do the following things

  • It creates and manages an HTTP connection manager for URL
  • It uses the Jackson library for serializing and deserializing the java object from JSOn data
  • getForObject accepts URL and Object class and returns the response in the java object

This is the way how Resttemplate simplified java objects converted from JSON.

How to consume paginated response with resttemplate in spring

Pagination is data retrieving logic that returns few records when there are more records with paginated data.

For example, if API returns the following JSON response.

{"content":[{"id":1,"mobile":"1234","email":test@gmail,"designation":"Manager","department":"Finance "}],"last":true,"totalElements":1,"totalPages":1,"sort":[],"numberOfElements":1,"first":true,"size":20,"number":0,"empty":false}

API returns pageable data that has the following attributes

  • content attribute holds actual data returned from API
  • last true means last page
  • size number of records to return in a single call
  • totalPages - returns the total pages of all records
  • sort - will give sorting is enabled on any properties
  • first - first page or not

If API returns these json data, We have do customize handle this pageable response.

First, let’s create PaginatedResponse.java which extends PageImpl from the spring framework.


import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.databind.JsonNode;
import org.springframework.data.domain.PageImpl;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import java.util.ArrayList;
import java.util.List;

public class PaginatedResponse<T> extends PageImpl<T> {
    @JsonCreator(mode = JsonCreator.Mode.PROPERTIES)
    public PaginatedResponse(@JsonProperty("content") List<T> content,
                            @JsonProperty("number") int number,
                            @JsonProperty("size") int size,
                            @JsonProperty("totalElements") Long totalElements,
                            @JsonProperty("pageable") JsonNode pageable,
                            @JsonProperty("last") boolean last,
                            @JsonProperty("totalPages") int totalPages,
                            @JsonProperty("sort") JsonNode sort,
                            @JsonProperty("first") boolean first,
                            @JsonProperty("first") boolean first,
                            @JsonProperty("empty") boolean empty) {

        super(content, PageRequest.of(number, size), totalElements);
    }

    public PaginatedResponse(List<T> content, Pageable pageable, long total) {
        super(content, pageable, total);
    }

    public PaginatedResponse(List<T> content) {
        super(content);
    }

    public PaginatedResponse() {
        super(new ArrayList<>());
    }
}

In consuming API, the code is as follows

We have to use ParameterizedTypeReference provides a type reference to the jackson object wrapper to convert the PaginatedResponse with the format for Employee class

ParameterizedTypeReference<PaginatedResponse<Employee>> responseType = new ParameterizedTypeReference<PaginatedResponse<Employee>>() { };

ResponseEntity<RestResponsePage<Employee>> result = restTemplate.exchange(url, HttpMethod.GET, null/, responseType);

List<Employee> employeeList = result.getBody().getContent();

Conclusion

Consuming REST API with plan object is straightforward, But the paginated response format needs to play with spring classes to return the correct format.

For any reason, if the returned response is different from the above, You have to modify it accordingly.