1. spring-test 모듈
- 외부 시스템과 연결하지 않고도 통합테스트를 하도록 지원함
- 다양한 테스트 프레임워크와 연동됨 (JUnit, TestNG 등)
2. 테스트 클래스에 의존성 주입
TestContext
- 테스트 실행 중의 상태와 메타데이터를 캡슐화한 객체입니다.
- 전체 테스트 컨텍스트의 흐름을 관리
기능 | 설명 |
🔁 ApplicationContext 관리 |
테스트 시 사용할 스프링 컨텍스트(ApplicationContext)를 생성하고, 재사용을 위해 캐싱함
|
💉 의존성 주입 지원 |
@Autowired, @Value, @MockBean 등을 통해 테스트 클래스에도 빈 주입 가능
|
🔄 트랜잭션 관리 |
@Transactional을 테스트에 적용해 자동 롤백 같은 트랜잭션 기능 제공
|
🔧 테스트 라이프사이클 관리 |
@BeforeEach, @AfterEach, @BeforeAll, @AfterAll 등의 실행 타이밍을 조절함
|
🧪 테스트 컨텍스트 정보 제공 |
테스트 클래스, 메서드, 어노테이션 등 다양한 테스트 메타데이터를 제공함
|
흐름
- @ExtendWith(SpringExtension.class)로 테스트 시작
- Spring이 내부적으로 TestContext 객체 생성
- @ContextConfiguration 또는 @SpringBootTest로 ApplicationContext 로딩
- TestContext가 ApplicationContext를 캐싱
- 테스트 클래스에 DI 수행 (@Autowired, etc.)
- 테스트 메서드 실행
관련 클래스
클래스 | 설명 |
TestContext |
테스트에 대한 상태 정보를 담고 있음
|
TestContextManager |
테스트 실행 시 TestContext를 관리하는 실제 매니저
|
SpringExtension |
JUnit 5에서 TestContextManager를 사용하는 Extension
|
3. 컨텍스트 관리 및 캐싱
- 테스트 클래스간 ApplicationContext를 재사용하여 사용
어노테이션 | 설명 | 비고 |
@ExtendWith(SpringExtension.class) | JUnit 5에서 Spring TestContext Framework 연동 | JUnit5에서는 필수 (JUnit4의 @RunWith 대체) |
@ContextConfiguration(...) | 테스트 시 로딩할 Spring Bean 설정 지정 (@Configuration or XML) |
classes, locations 등으로 지정 |
예제
더보기
@Configuration
public class AppConfig {
@Bean
public HelloService helloService() {
return new HelloService();
}
}
public class HelloService {
public String sayHello() {
return "hello spring test!";
}
}
@ExtendWith(SpringExtension.class)
@ContextConfiguration(classes = AppConfig.class)
public class HelloServiceTest1 {
@Autowired
private ApplicationContext context;
@Autowired
private HelloService helloService;
@Test
void testHelloService1() {
System.out.println("HelloServiceTest1의 context: " + context);
assertEquals("hello spring test!", helloService.sayHello());
}
}
@ExtendWith(SpringExtension.class)
@ContextConfiguration(classes = AppConfig.class)
public class HelloServiceTest2 {
@Autowired
private ApplicationContext context;
@Autowired
private HelloService helloService;
@Test
void testHelloService2() {
System.out.println("HelloServiceTest2의 context: " + context);
assertEquals("hello spring test!", helloService.sayHello());
}
}
HelloServiceTest1의 context: org.springframework.context.support.GenericApplicationContext@6ed3f258, started on Mon Apr 21 01:29:33 KST 2025
HelloServiceTest2의 context: org.springframework.context.support.GenericApplicationContext@6ed3f258, started on Mon Apr 21 01:29:33 KST 2025
4. 트랜잭션 관리
- 테스트 격리: 각 테스트별 자동 롤백을 수행하므로 독립적으로 실행되며, 이전 테스트의 DB 상태가 영향을 미치지 않음.
- @Commit 사용: 특정 테스트에 대해서는 DB 변경을 실제로 반영할 수 있음.
예제
더보기
@SpringJUnitConfig(DatabaseConfig.class)
public class MemberRepositoryTest {
@Autowired
private MemberRepository memberRepository;
@Test
@Transactional
void testCreateMember() {
memberRepository.save("noah");
Member member = memberRepository.findUserByUsername("noah");
assertEquals("noah", member.getUsername());
}
}
테스트 결과를 db에 반영하기
@SpringJUnitConfig(DatabaseConfig.class)
public class MemberRepositoryTest {
@Autowired
private MemberRepository memberRepository;
@Test
@Transactional
@Commit
void testCreateMember() {
memberRepository.save("noah");
Member member = memberRepository.findUserByUsername("noah");
assertEquals("noah", member.getUsername());
}
}
5. 지원 클래스
Spring은 통합 테스트를 쉽게 작성할 수 있도록 도와주는 추상 클래스들을 제공합니다.
항목 | 설명 |
ApplicationContext 접근 |
테스트 내에서 Bean을 가져와 직접 사용하거나 검증할 수 있습니다.
|
JdbcTemplate 사용 |
SQL을 직접 실행해서 DB 상태를 확인하거나 테스트 전후 검증에 사용할 수 있습니다.
|
공통 추상 클래스 작성 |
여러 테스트에서 공통적으로 필요한 설정, 유틸을 포함한 AbstractIntegrationTest와 같은 클래스를 만들어 상속하면 좋습니다.
|
출처
'Spring > Spring Test' 카테고리의 다른 글
[Spring][Test] 3. Testing Annotations (1) | 2025.04.21 |
---|---|
[Spring][Test] 1. Unit Testing (2) | 2025.04.19 |