Saturday 3 August 2019

Spring Boot: Testing controller or REST APIs


This is continuation to my previous post. In my previous post, I explained how to test service layer.

You can download previous working application from this link.

In this post, I am going to explain how to test actual REST API.

Step 1: Annotate the test class with @RunWith and @SpringBootTest annotations.
@RunWith(SpringJUnit4ClassRunner.class)
@SpringBootTest(classes = App.class, webEnvironment = WebEnvironment.RANDOM_PORT)
public class EmployeeControllerIntegrationTest {

}

SpringJUnit4ClassRunner is a custom extension of JUnit's BlockJUnit4ClassRunner which provides functionality of the Spring TestContext Framework to standard JUnit tests.

When a class is annotated with @RunWith or extends a class annotated with @RunWith, JUnit will invoke the class it references to run the tests in that class instead of the runner built into Junit.

@ SpringBootTest annotation should be specified on a test class that runs Spring Boot based tests.

Step 2: Autowire TestRestTemplate.

@Autowired
private TestRestTemplate restTemplate;

Step 3: Inject web application port that allocated at run time.
@LocalServerPort
int randomServerPort;


Step 4: Write the test cases using TestRestTemplate object.
@Test
public void testCreateEmployee() throws URISyntaxException {
 final String baseUrl = "http://localhost:" + randomServerPort + "/api/v1/employees/";
 URI uri = new URI(baseUrl);

 HttpHeaders headers = new HttpHeaders();
 headers.set("content-type", "application/json");

 Employee emp = new Employee();
 emp.setFirstName("Lahari");
 emp.setLastName("Gurram");

 HttpEntity<Employee> request = new HttpEntity<>(emp, headers);

 ResponseEntity<Employee> result = restTemplate.postForEntity(uri, request, Employee.class);

 assertEquals(201, result.getStatusCodeValue());

}

Complete source code looks like below.


EmployeeControllerIntegrationTest.java
package com.sample.app.controller;

import static org.junit.Assert.assertEquals;

import java.net.URI;
import java.net.URISyntaxException;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.boot.test.web.client.TestRestTemplate;
import org.springframework.boot.web.server.LocalServerPort;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.ResponseEntity;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;

import com.sample.app.App;
import com.sample.app.model.Employee;

import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;

@RunWith(SpringJUnit4ClassRunner.class)
@SpringBootTest(classes = App.class, webEnvironment = WebEnvironment.RANDOM_PORT)
public class EmployeeControllerIntegrationTest {

 @Autowired
 private TestRestTemplate restTemplate;

 @LocalServerPort
 int randomServerPort;

 @Test
 public void testCreateEmployee() throws URISyntaxException {
  final String baseUrl = "http://localhost:" + randomServerPort + "/api/v1/employees/";
  URI uri = new URI(baseUrl);

  HttpHeaders headers = new HttpHeaders();
  headers.set("content-type", "application/json");

  Employee emp = new Employee();
  emp.setFirstName("Lahari");
  emp.setLastName("Gurram");

  HttpEntity<Employee> request = new HttpEntity<>(emp, headers);

  ResponseEntity<Employee> result = restTemplate.postForEntity(uri, request, Employee.class);

  assertEquals(201, result.getStatusCodeValue());

 }

}


Total project structure looks like below.

You can find complete working application from this link.



Previous                                                    Next                                                    Home

No comments:

Post a Comment