Mockito’s Mock Methods

Dev.Hammy·2024년 4월 1일

Mockito_Tutorial

목록 보기
3/21

1. Overview

이 튜토리얼에서는 Mockito API의 표준 정적 mock 메소드의 다양한 용도를 설명합니다.

Mockito 프레임워크(예: Mockito Verify 또는 Mockito When/Then)에 초점을 맞춘 다른 기사에서와 마찬가지로 아래 표시된 MyList 클래스는 테스트 사례에서 모의할 collaborator로 사용됩니다.

public class MyList extends AbstractList<String> {

    @Override
    public String get(int index) {
        return null;
    }

    @Override
    public int size() {
        return 1;
    }
}

2. Simple Mocking

mock 메소드의 가장 간단한 오버로드된 변형은 모의할 클래스에 대한 단일 매개변수를 갖는 것입니다:

public static <T> T mock(Class<T> classToMock)

우리는 클래스를 모의하고 기대치를 설정하기 위해 이 메소드를 사용할 것입니다:

MyList listMock = mock(MyList.class);
when(listMock.add(anyString())).thenReturn(false);

그런 다음 모의 객체에서 메서드를 실행합니다.

boolean added = listMock.add(randomAlphabetic(6));

다음 코드는 모의 객체에서 add 메서드를 호출했음을 확인합니다. 호출은 이전에 설정한 기대와 일치하는 값을 반환합니다.

verify(listMock).add(anyString());
assertThat(added).isFalse();

3. Mocking With Mock's Name

이 섹션에서는 mock 메소드의 이름을 지정하는 인수와 함께 제공되는 모의 메소드의 또 다른 변형을 다룰 것입니다:

public static <T> T mock(Class<T> classToMock, String name)

일반적으로 모의 이름은 작업 코드와 아무런 관련이 없습니다. 그러나 검증 오류를 추적하기 위해 모의 이름을 사용하므로 디버깅에 도움이 될 수 있습니다.

실패한 확인으로 인해 발생한 예외 메시지에 제공된 모의 이름이 포함되어 있는지 확인하기 위해 assertThatThrownBy를 사용합니다.
다음 코드에서는 MyList 클래스에 대한 모의 클래스를 만들고 이름을 myMock으로 지정합니다.

MyList listMock = mock(MyList.class, "myMock");

그런 다음 모의 메서드에 대한 기대치를 설정하고 실행합니다.

when(listMock.add(anyString())).thenReturn(false);
listMock.add(randomAlphabetic(6));

다음으로, assertThatThrownBy 내에서 확인을 호출하고 발생한 예외의 인스턴스를 확인하겠습니다.

assertThatThrownBy(() -> verify(listMock, times(2)).add(anyString()))
    .isInstanceOf(TooFewActualInvocations.class)

또한 모의 객체에 대한 정보를 포함해야 한다는 예외 메시지를 확인할 수도 있습니다.

assertThatThrownBy(() -> verify(listMock, times(2)).add(anyString()))
    .isInstanceOf(TooFewActualInvocations.class)
    .hasMessageContaining("myMock.add");

발생한 예외 메시지는 다음과 같습니다.

org.mockito.exceptions.verification.TooLittleActualInvocations:
myMock.add(<any>);
Wanted 2 times:
at com.baeldung.mockito.MockitoMockTest
  .whenUsingMockWithName_thenCorrect(MockitoMockTest.java:...)
but was 1 time:
at com.baeldung.mockito.MockitoMockTest
  .whenUsingMockWithName_thenCorrect(MockitoMockTest.java:...)

보시다시피, 예외 메시지에는 모의 이름이 포함되어 있는데, 이는 검증에 실패한 경우 실패 지점을 찾는 데 유용합니다.

4. Mocking With Answer

여기서는 생성 시 상호 작용에 대한 모의 응답에 대한 전략을 구성하는 mock 변형의 사용을 보여줍니다. Mockito 문서의 이 mock 메서드 시그니처는 다음과 같습니다.

public static <T> T mock(Class<T> classToMock, Answer defaultAnswer)

Answer 인터페이스 구현의 정의부터 시작해 보겠습니다.

class CustomAnswer implements Answer<Boolean> {

    @Override
    public Boolean answer(InvocationOnMock invocation) throws Throwable {
        return false;
    }
}

모의 생성을 위해 위의 CustomAnswer 클래스를 사용합니다.

MyList listMock = mock(MyList.class, new CustomAnswer());

메서드에 대한 기대치를 설정하지 않으면 CustomAnswer 유형으로 구성된 기본 답변이 적용됩니다. 이를 증명하기 위해 기대 설정 단계를 건너뛰고 메서드 실행으로 넘어갑니다.

boolean added = listMock.add(randomAlphabetic(6));

다음 확인 및 주장은 Answer 인수가 있는 모의 메서드가 예상대로 작동했음을 확인합니다.

verify(listMock).add(anyString());
assertThat(added).isFalse();

5. Mocking With MockSettings

이 글에서 우리가 다룰 마지막 모의 메소드는 MockSettings 유형의 매개변수를 가진 변형입니다. 우리는 비표준 모의를 제공하기 위해 이 오버로드된 메서드를 사용합니다.

invocationListeners를 사용하여 현재 모의에서 메서드 호출을 위한 리스너 등록, serializable으로 직렬화 구성, spiedInstance로 감시할 인스턴스 지정, 생성자 사용을 시도하도록 Mockito 구성 등 MockSettings 인터페이스의 메서드에서 지원되는 여러 사용자 정의 설정이 있습니다. useConstructor 등을 사용하여 모의 객체를 인스턴스화할 때

편의를 위해 이전 섹션에서 소개한 CustomAnswer 클래스를 재사용하여 기본 답변을 정의하는 MockSettings 구현을 생성하겠습니다.

MockSettings 객체는 팩토리 메소드에 의해 인스턴스화됩니다.

MockSettings customSettings = withSettings().defaultAnswer(new CustomAnswer());

우리는 새로운 모의 객체를 생성할 때 해당 설정 객체를 사용할 것입니다:

MyList listMock = mock(MyList.class, customSettings);

이전 섹션과 유사하게 MyList 인스턴스의 add 메소드를 호출하고 MockSettings 인수가 있는 mock 메소드가 예상대로 작동하는지 확인합니다.

boolean added = listMock.add(randomAlphabetic(6));

verify(listMock).add(anyString());
assertThat(added).isFalse();

0개의 댓글