개발/Spring Boot

Spring Boot 시리즈 14편 – API 테스트 자동화 전략: RestAssured, MockMvc, TestContainers 실전 가이드

B컷개발자 2025. 4. 26. 00:14
Spring Boot에서 REST API 테스트를 자동화하는 전략을 소개합니다. MockMvc, RestAssured, TestContainers를 활용한 통합 테스트 구조와 품질 확보 방법을 설명합니다.

 


 

Spring Boot 시리즈 14편 – API 테스트 자동화 전략: RestAssured, MockMvc, TestContainers 실전 가이드

 

API는 빠르게 만들 수 있지만, 안정적으로 운영되도록 유지하는 일은 훨씬 어렵습니다.

테스트 코드가 없거나, 일관성이 없거나, 실제 운영 환경과 동떨어진 테스트는 결국 서비스 장애로 이어질 수 있습니다.

 

이번 편에서는 Spring Boot 환경에서 REST API를 MockMvc, RestAssured, TestContainers를 통해

개발 → 통합 → 환경 검증까지 이어지는 테스트 전략을 실제 사례 중심으로 정리합니다.

 


 

📌 1. API 테스트는 왜 자동화되어야 하나?

이유설명

회귀 테스트 코드 변경 시 기존 기능이 깨지지 않았는지 확인
스펙 일치 확인 Swagger 또는 명세서와 실제 동작 일치 여부 검증
배포 안정성 확보 CI/CD 파이프라인에서 테스트 자동 실행
문서화와 테스트 연동 테스트 → RestDocs 기반 문서 자동 생성 가능

 

 


 

✅ 2. 단위 테스트 vs 통합 테스트 vs 시스템 테스트

분류범위도구주로 검증하는 것

단위 테스트 한 클래스 또는 함수 JUnit, Mockito 비즈니스 로직 정확성
통합 테스트 API 전체 흐름 MockMvc, RestAssured 컨트롤러 ↔ 서비스 ↔ DB
시스템 테스트 실제 환경 구성 TestContainers 환경 포함 전체 시스템 동작

 

 


 

🔧 3. MockMvc를 활용한 API 통합 테스트

 

 

1️⃣ 기본 설정

@SpringBootTest
@AutoConfigureMockMvc
class UserApiTest {

    @Autowired
    private MockMvc mockMvc;

    @Test
    void 사용자_등록_성공() throws Exception {
        String json = """
            {
              "email": "test@example.com",
              "password": "1234",
              "name": "홍길동"
            }
        """;

        mockMvc.perform(post("/api/users")
                .contentType(MediaType.APPLICATION_JSON)
                .content(json))
            .andExpect(status().isOk())
            .andExpect(jsonPath("$.success").value(true));
    }
}
Spring Context 전체를 로딩하여 실제 API 흐름을 검증할 수 있습니다.

 


 

✅ 특징

 

  • 빠르고 설정 간단
  • Spring Security, 필터 적용 여부를 함께 테스트 가능
  • 하지만 실제 HTTP 포트는 사용하지 않음 → 외부 클라이언트 테스트는 불가

 


 

🌐 4. RestAssured 기반 실제 HTTP 요청 테스트

 

 

1️⃣ 의존성 추가

testImplementation 'io.rest-assured:rest-assured:5.3.0'

 

 


 

2️⃣ RestAssured 테스트 예제

@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@TestMethodOrder(MethodOrderer.OrderAnnotation.class)
class UserRestApiTest {

    @LocalServerPort
    int port;

    @Test
    void 사용자_등록_성공() {
        given()
            .port(port)
            .contentType(ContentType.JSON)
            .body("""
                {
                  "email": "rest@test.com",
                  "password": "abcd",
                  "name": "테스터"
                }
            """)
        .when()
            .post("/api/users")
        .then()
            .statusCode(200)
            .body("success", equalTo(true));
    }
}

 

✅ 장점

 

  • 실제 HTTP 요청을 통해 통합 테스트 가능
  • Swagger 명세와 실제 응답 일치 여부 검증에 적합
  • 클라이언트 UX 시나리오 테스트에 매우 유리

 


 

🐳 5. TestContainers – 환경 통합 테스트

 

 

1️⃣ 목적

 

  • 실제 DB(MySQL, PostgreSQL 등) 컨테이너를 띄워 통합 테스트 실행
  • CI 환경에서도 운영 환경과 동일한 조건에서 테스트 가능

 


 

2️⃣ PostgreSQL 컨테이너 예시

@Testcontainers
@SpringBootTest
class ContainerizedApiTest {

    @Container
    static PostgreSQLContainer<?> postgres = new PostgreSQLContainer<>("postgres:13")
        .withDatabaseName("testdb")
        .withUsername("test")
        .withPassword("test");

    @DynamicPropertySource
    static void overrideProps(DynamicPropertyRegistry registry) {
        registry.add("spring.datasource.url", postgres::getJdbcUrl);
        registry.add("spring.datasource.username", postgres::getUsername);
        registry.add("spring.datasource.password", postgres::getPassword);
    }

    @Test
    void DB_연동_및_API_정상동작() {
        // 테스트 코드 작성
    }
}

 

 


 

🧠 실무 전략 요약

전략 항목설명

테스트 클래스 구조 기능별 Controller 단위로 테스트 클래스 분리
테스트 데이터 관리 @Sql 또는 Fixture 유틸로 초기화
실패 케이스 포함 인증 실패, 유효성 오류 등도 반드시 검증
테스트 명명 규칙 한글로 시나리오 중심 (회원가입_성공_시_200응답)
CI 연동 GitHub Actions, GitLab CI에서 test 자동 실행 구성

 

 


 

✅ 마무리 요약

항목요약

MockMvc 빠른 테스트, Spring Context 내에서 API 흐름 검증
RestAssured 실제 포트를 사용하는 HTTP 요청 기반 테스트
TestContainers 실환경 DB/외부 시스템과 함께 전체 통합 테스트
실무 팁 실패 케이스까지 포함 + 테스트 환경 재현성 유지 중요
CI 적용 PR마다 테스트 실행 → 품질 보장

 

 


 

📌 다음 편 예고

 

Spring Boot 시리즈 15편: 운영 환경 배포 전략 – Docker, 무중단 배포, Spring Boot + CI/CD 흐름 정리

LIST