This is a short series of how to use Spring in integration testing and unit testing.
ConfigurationsMocking

Testing a REST API
A custom configurationConfiguration logic

First, a couple of words about Spring in general as a dependency injection framework. One of the best things in Spring is its simplicity of injection. Regardless of where you are, you pop an @Autowired annotation on a class variable (which could be the test class), and it’s ready for injection. Since it’s injecting the same instance regardless of class, setup for mocks is easy. And regardless of how many layers away the object will be injected, the test has access to it, and doesn’t need to pass it between layers, which requires less code. That is always a good thing.

On the registeration side, with @Configuration classes, you can configure exactly and easily what to inject. Spring Boot allows you to do a bit more with easily bootstrapping a project, along with a bit more help for unit tests and integration tests.

All these make it easy to use (and abuse) writing integration tests. Let’s take a look at a couple of scenarios for integration testing.

For our first example, we have a REST API, that inside it calls a dependency. In integration testing APIs like this, we usually go all the way to the back, but even then, we might want to mock something at the back end, mostly for controlling behavior of our integration test.

First, I want to inject a real object I create. In a @Configuration class I put under the test folder, I create this configuration:

@Configuration
public class POJOInjectionConfiguration {
	
	@Bean
	public Student student() {
		return new Student("Gil", "Star Wars");
		
	}
}

Then in the integration test I’ll use the @Configuration class:

@RunWith(SpringRunner.class)
@ContextConfiguration(classes = { POJOInjectionConfiguration.class })
public class RealStudioPOJOInjected {

	@Autowired
	private Student student;
	
	@Test
	public void nameOfInjectedObject() {
		assertTrue(student.getName() == "Gil");
	}
}

That is more of an explanation how Spring works, and obviously, not that useful. In actual integration testing scenarios I use this for injecting POJOs in internal layers, or inject objects that will call dependcies I mock.

If I want to inject a mock instead (let’s say Student wasn’t a POJO), I’ll use a different @Configuration class:

@Configuration
public class MockInjectionConfiguration {
	
	@Bean
	public Student student() {
		Student mockStudent = Mockito.mock(Student.class); 				
		when(mockStudent.getName()).thenReturn("Gil");
		when(mockStudent.getSubject()).thenReturn("Star Wars");
		return mockStudent;
	}
}

And then I can use it in a test:

@RunWith(SpringRunner.class)
@ContextConfiguration(classes = { MockInjectionConfiguration.class })
public class MockStudentInjected {

	@Autowired
	private Student student;
	
	@Test
	public void nameOfMockReturned() {
		assertTrue(student.getName() == "Gil");
	}
}

Now that’s in the test, I can add mocking behavior.

That’s the basic @Configuration stuff. We’ll continue the discussion on configurations and mocking next time.


0 Comments

Leave a Reply

Avatar placeholder

Your email address will not be published. Required fields are marked *