View
1. JUnit5 - Assertion
JUnit Jupiter는 다양한 Assertion 메서드가 포함되어있다. Assertion 클래스를 살펴보면 메서드는 모두 static 메서드이고, 오버로딩을 통해 다양한 타입을 지원하고 있다.
다양한 Assertion 메서드를 살펴보자.
- assertEqulas(expected, actual)
- 실제 값이 기대한 값과 같은지 확인
- assertNotNull(actual)
- 실제 값이 null이 아닌지 확인
- assertTrue(boolean)
- 다음 조건이 True인지 확인
- assertAll(executables)
- 모든 구문을 확인
- functional Interface인 excutables 타입을 매개변수로 받는다.
- assertThrows(expectedType, executable)
- 예외 발생 확인
- assertTimeout(duration, executable)
- 특정 시간안에 실행이 완료되는지 확인
Supplier와 람다식
마지막 매개변수로 message를 String형태로 생성하여 메시지를 출력할 수 있다.
예를들면 아래의 코드와 같이 테스트 결과와 함께 메시지를 출력할 수 있다.
@Test
@DisplayName("스터디 시작")
void start_study() {
Study study = new Study();
assertNotNull(study);
// 메시지를 String 형태로 생성하면, 테스트가 성공하던 실패하던 문자열 연산을 매번 실행한다.
assertEquals(StudyStatus.DRAFT, study.getStatus(),
"스터디를 처음 시작하면 " + StudyStatus.DRAFT + " 상태다.");
위와 같이 메시지를 String 형태로 제공하게 되면 메시지를 출력할 수 있다. 하지만 이는 테스트의 실패, 성공 관계없이 문자열 연산을 실행한다.
만약 복잡한 문자열 연산이 들어가거나, 성능을 조금이라도 고려하는 테스트라면 Supplier<String> 타입의 인스턴스를 이용해서 이러한 연산을 비용을 줄일 수 있다.
Supplier<T>는 Functional Interface이다. 이를 사용하게 되면 테스트가 실패한 시점에만 호출되어 연산을 실행하기 때문에 연산 비용을 줄일 수 있는 것이다. 매개변수는 없고 리턴타입만 가지고있다.
Supplier<T>를 이용하여 위와 같은 연산을 표현하면, 아래와 같은 코드를 만들 수 있다.
@Test
@DisplayName("스터디 시작")
void start_study() {
Study study = new Study();
assertNotNull(study);
// Supplier를 이용한 메시지
assertEquals(StudyStatus.DRAFT, study.getStatus(), new Supplier<String>() {
@Override
public String get() {
return "스터디를 처음 만들면 DRAFT 상태다.";
}
});
}
하지만 위와 같이 메시지를 생성하면 비용은 줄일 수 있지만 코드가 길어지는 단점이 있다. 이 또한 Java 8에서 추가된 람다식을 이용하면 코드를 간결하게 표현할 수 있게 된다.
@Test
@DisplayName("스터디 시작")
void start_study() {
Study study = new Study();
assertNotNull(study);
// 람다식을 사용하면 간결한 표현이 가능하다.
assertEquals(StudyStatus.DRAFT, study.getStatus(), () -> "스터디를 처음 만들면 DRAFT 상태다.");
}
AssertAll() 메서드
한 테스트에 여러개의 assert 메서드를 이용해 테스트를 진행할 때, 최상단의 assert 메서드에서 테스트가 깨지면 그 아래 테스트 코드는 실행되지 않기 때문에 값에 대한 명확한 검증이 어려워진다.
예를들면,
@Test
@DisplayName("스터디 시작")
void start_study() {
Study study = new Study();
assertNotNull(study); // <- 여기서 오류 발생시 밑의 코드는 실행되지 않는다.
assertEquals(StudyStatus.DRAFT, study.getStatus(), () -> "스터디를 처음 만들면 DRAFT 상태다.");
assertTrue(study.getLimit() -> 0, "스터디 인원 수는 0보다 커야합니다");
}
위와 같은 경우에는 assertNotNull(study); 이후의 테스트가 깨지는지 검증할 방법이 없다. 이러한 문제를 해결하기 위해서는 assertAll() 메서드를 이용하면 된다.
assertAll 메서드안에 assert 메서드를 선언해 사용할 경우 오류가 발생해도 모든 assert 메서드를 실행하게 된다.
@Test
@DisplayName("스터디 시작")
void start_study() {
Study study = new Study();
assertAll(
() -> assertNotNull(study),
() -> assertEquals(StudyStatus.DRAFT, study.getStatus(),
() -> "스터디를 처음 만들면 DRAFT 상태다."),
() -> assertTrue(study.getLimit() -> 0, "스터디 인원 수는 0보다 커야합니다")
);
}
위와 같이 assertAll 메서드를 이용하면 각 값에 대한 명확한 테스트 결과를 알 수 있게 된다.
'BackEnd > Java' 카테고리의 다른 글
[Java8] 자바에서 제공하는 함수형 인터페이스 (0) | 2021.05.04 |
---|---|
[Java8] 함수형 인터페이스와 람다 표현식 (0) | 2021.04.19 |
[Java] 역직렬화(Deserialize) (0) | 2020.07.16 |
[Java] JUnit5을 이용한 테스트 시작하기 (0) | 2020.07.03 |
[Java] - 직렬화(Serialize) (0) | 2020.06.17 |