랜덤하게 11부터 99 이하의 수를 생성하는 서비스를 만들다고 가정할 때
1. 아래와 같이 서비스의 interface를 선언한다.
package microservices.book.multiplication.service;
public interface RandomGeneratorService {
/**
* @return 무작위로 만든 11 이상 99 이하의 인수
*/
int generateRandomFactor();
}
package microservices.book.multiplication.service;
import microservices.book.multiplication.domain.Multiplication;
public interface MultiplicationService {
/**
* 두 개의 무작위 인수를 인수를 담은 {@link Multiplication} 객체를 생성한다.
* 무작위로 생성되는 숫자의 범위는 11~99.
*
* @return 무작위 인수를 담은 {@link Multiplication} 객체
*/
Multiplication createRandomMultiplication();
}
package microservices.book.multiplication.service;
import microservices.book.multiplication.domain.Multiplication;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@Service
class MultiplicationServiceImpl implements MultiplicationService {
private RandomGeneratorService randomGeneratorService;
@Autowired
public MultiplicationServiceImpl(RandomGeneratorService randomGeneratorService) {
this.randomGeneratorService = randomGeneratorService;
}
@Override
public Multiplication createRandomMultiplication() {
int factorA = randomGeneratorService.generateRandomFactor();
int factorB = randomGeneratorService.generateRandomFactor();
return new Multiplication(factorA, factorB);
}
}
2. 서비스의 테스트 코드를 만든다.
package microservices.book.multiplication.service;
import microservices.book.multiplication.domain.Multiplication;
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.mock.mockito.MockBean;
import org.springframework.test.context.junit4.SpringRunner;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.BDDMockito.given;
@RunWith(SpringRunner.class)
@SpringBootTest
public class MultiplicationServiceTest {
@MockBean
private RandomGeneratorService randomGeneratorService;
@Autowired
private MultiplicationService multiplicationService;
@Test
public void createRandomMultiplicationTest() {
// given (randomGeneratorService 가 처음에 50, 나중에 30을 반환하도록 설정)
given(randomGeneratorService.generateRandomFactor()).willReturn(50, 30);
// when
Multiplication multiplication = multiplicationService.createRandomMultiplication();
// assert
assertThat(multiplication.getFactorA()).isEqualTo(50);
assertThat(multiplication.getFactorB()).isEqualTo(30);
assertThat(multiplication.getResult()).isEqualTo(1500);
}
}
-
RandomGeneratorService는 인터페이스만 있을 뿐 아직 구현체가 없는 상태로 테스트가 불가능하다.
-
테스트 코드에서 @MockBean 선언을 통해 목(mock-up, 모형) 객체를 주입한다.
-
given을 통해 randomGeneratorService의 generateRandonFactor()를 호출했을 때 리턴값을 설정한다.
-
given(randomGeneratorService.generateRandomFactor()).willReturn(50, 30);
-
maven에서 테스트 방법
mvn -Dtest=MultiplicationServiceTest test
given의 선언부
package org.mockito;
public class BDDMockito extends org.mockito.Mockito {
public BDDMockito() { /* compiled code */ }
public static <T> org.mockito.BDDMockito.BDDMyOngoingStubbing<T> given(T methodCall) { /* compiled code */ }
public static <T> org.mockito.BDDMockito.Then<T> then(T mock) { /* compiled code */ }
public static org.mockito.BDDMockito.BDDStubber willThrow(java.lang.Throwable toBeThrown) { /* compiled code */ }
...
}
public static interface BDDMyOngoingStubbing <T> {
org.mockito.BDDMockito.BDDMyOngoingStubbing<T> willAnswer(org.mockito.stubbing.Answer<?> answer);
org.mockito.BDDMockito.BDDMyOngoingStubbing<T> will(org.mockito.stubbing.Answer<?> answer);
org.mockito.BDDMockito.BDDMyOngoingStubbing<T> willReturn(T t);
org.mockito.BDDMockito.BDDMyOngoingStubbing<T> willReturn(T t, T... ts);
org.mockito.BDDMockito.BDDMyOngoingStubbing<T> willThrow(java.lang.Throwable... throwables);
org.mockito.BDDMockito.BDDMyOngoingStubbing<T> willThrow(java.lang.Class<? extends java.lang.Throwable>... classes);
org.mockito.BDDMockito.BDDMyOngoingStubbing<T> willCallRealMethod();
<M> M getMock();
}
}