방법론/Test

ReflectionTestUtils

manchesterandthecity 2025. 7. 16. 21:15

🔍 ReflectionTestUtils란?

- 테스트에서 private 필드와 메서드도 강제로 다뤄야 할 때!


✅ 1. ReflectionTestUtils란?

ReflectionTestUtils는 Spring Test 모듈에서 제공하는 유틸리티 클래스입니다.
주로 테스트 코드에서 접근 제한(private) 되어 있는 필드나 메서드를
리플렉션(reflection)을 이용해 강제로 접근하거나 값을 설정할 때 사용됩니다.

📍 의존성 추가 (Gradle)

dependencies {
    testImplementation 'org.springframework:spring-test'
}
  • Spring Boot를 사용 중이라면 별도 추가 필요 없음
    → spring-boot-starter-test 안에 이미 포함돼 있습니다.
dependencies {
    testImplementation 'org.springframework.boot:spring-boot-starter-test'
}

✔ 위 starter에는 spring-test, junit, mockito, assertj 등 대부분의 테스트 유틸리티가 함께 포함되어 있어 별도로 추가하지 않아도 됩니다.


💡 왜 필요할까?

  • 객체의 private 필드 값을 강제로 세팅해야 할 때
  • setter나 생성자가 없는 클래스를 테스트해야 할 때
  • 캡슐화된 내부 상태를 검증하거나 조작해야 할 때

즉, 테스트 목적상 "강제 접근" 이 필요한 경우에 사용하는 도구입니다.


🧩 2. 주요 기능 요약

메서드 설명
setField() private 필드의 값을 강제로 설정
getField() private 필드 값을 강제로 가져옴
invokeMethod() private 메서드를 실행함

🧪 3. 사용 예제

📍 예제 클래스

public class UserService {
    private String secretKey = "default";

    private String encode(String value) {
        return value + ":" + secretKey;
    }
}

📌 setField() — 필드 값 강제 주입

UserService service = new UserService();

// private 필드 secretKey 값 변경
ReflectionTestUtils.setField(service, "secretKey", "newKey");

📌 getField() — 필드 값 읽기

String key = (String) ReflectionTestUtils.getField(service, "secretKey");
System.out.println(key); // newKey

📌 invokeMethod() — private 메서드 실행

String result = (String) ReflectionTestUtils.invokeMethod(service, "encode", "token");
System.out.println(result); // token:newKey

🛠 4. 생성자 없는 클래스 테스트

@NoArgsConstructor(access = AccessLevel.PRIVATE)
public class Token {
    private String value;
}

➡ 테스트 코드에서 강제로 인스턴스 생성 및 필드 주입 가능:

Token token = new Token();
ReflectionTestUtils.setField(token, "value", "abc123");

⚠️ 5. 주의사항

항목 설명
리플렉션은 느리다 성능이 중요한 상황에는 지양
캡슐화 깨짐 실제 코드에서는 절대 사용 금지 (테스트 전용 도구)
필드명/메서드명 오타 주의 컴파일러가 체크하지 않음 (런타임 오류)

✅ 마무리 정리

항목 설명
클래스 org.springframework.test.util.ReflectionTestUtils
주요 용도 테스트에서 private 필드/메서드 조작
주요 메서드 setField(), getField(), invokeMethod()
주 사용 상황 생성자/세터 없는 객체, 내부 로직 검증, 레거시 테스트
주의사항 오용 주의, 성능 이슈, 리플렉션 한계 인식 필요

 

ReflectionTestUtils는 테스트의 "편법"이자 "마지막 수단"입니다.
하지만 꼭 필요한 경우에만 제한적으로 사용하면,
접근할 수 없었던 코드의 테스트 가능성을 넓혀주는 강력한 도구가 될 수 있습니다. 🛠