본문 바로가기

Spring

[Spring] 프로파일(profiles) 로딩 우선순위

👤 프로파일이란?

Spring 프로파일은 같은 애플리케이션이라도 실행 환경에 따라 다른 설정 파일이나 빈(Bean)을 사용할 수 있도록 해주는 기능이다.

 

사용 예시

  • 개발환경(dev): 로컬 DB 사용
  • 테스트환경(test): H2 메모리 DB 사용
  • 운영환경(prod): 실제 운영용 DB 사용

프로파일을 설정하는 방법

// 폴더 구조
src/
├── main/
│   └── resources/
│       ├── application.yml                # 공통 설정
│       ├── application-dev.yml            # 개발용
│       └── application-prod.yml           # 운영용
└── test/
    └── resources/
        └── application-test.yml           # 테스트 전용
# application.yml (기본 설정 파일)
spring:
  profiles:
    active: dev # 실행할 프로파일을 명시
# application-dev.yml
server:
  port: 8081

spring:
  datasource:
    url: jdbc:mysql://localhost:3306/dev_db
# application-test.yml
server:
  port: 8082

spring:
  datasource:
    url: jdbc:h2:mem:testdb
  • Spring Boot는 spring.profiles.active에 지정된 값(dev, test, prod 등)을 기준으로 해당 프로파일의 설정 파일을 자동으로 병합한다.

프로파일별 Bean 등록

@Configuration
public class MyConfig {

    @Bean
    @Profile("dev")
    public DataSource devDataSource() {
        // 개발용 DataSource
        return new HikariDataSource(...);
    }

    @Bean
    @Profile("prod")
    public DataSource prodDataSource() {
        // 운영용 DataSource
        return new HikariDataSource(...);
    }
}

 

  • @Profile("dev"): dev 프로파일일 때만 이 빈이 등록된다.
  • @Profile("prod"): 운영 환경에서만 등록된다.

프로파일 실행 방식 3가지

// (1) application.yml에서 설정
spring:
  profiles:
    active: dev
// (2) 커맨드라인에서 설정
java -jar app.jar --spring.profiles.active=prod

 

// (3) IntelliJ VM Options
-Dspring.profiles.active=test

 

테스트에서 프로파일 적용

// 방법 1: @ActiveProfiles 사용
@SpringBootTest
@ActiveProfiles("test")
class MyServiceTest {
    // application-test.yml 적용됨
    ...
}
// 방법 2: 테스트용 application-test.yml 사용
// 이 설정은 테스트 실행 시 자동으로 로드됩니다 (우선순위가 높음).
# src/test/resources/application-test.yml
spring:
  datasource:
    url: jdbc:h2:mem:testdb

🔢 Spring Boot 프로파일 로딩 우선순위

Spring Boot는 설정 파일(application.yml, application-{profile}.yml, application.properties 등)을 다음과 같은 우선순위로 로드한다. 중요한 건 뒤에 있는 파일이 앞 파일을 덮어씌운다는 점이다.

 

📊 우선순위 정리 (높은 순 → 낮은 순)

  1. @TestPropertySource, @SpringBootTest(properties = ...)
  2. application-test.yml (src/test/resources)
  3. application-{profile}.yml (예: application-dev.yml)
  4. application.yml (src/main/resources)

우선순위가 높은 설정이 우선적으로 적용되고, 같은 키가 있다면 이전 설정을 무시하고 새로운 값으로 대체한다는 뜻이다


🌟 테스트 환경에서의 로딩 우선순위

아주 간단한 예제를 통해 쉽게 알아보자. (설정 키는 app.name 하나라고 한다. 이 키는 설정 파일마다 다르게 정의되어 있다.)

app:
  name: 공통설정
app:
  name: 개발설정
app:
  name: 테스트설정

 

테스트 코드

@SpringBootTest
@ActiveProfiles("dev")
public class SampleTest {

    @Autowired
    Environment env;

    @Test
    void testProfileProperty() {
        System.out.println(env.getProperty("결과: app.name"));
    }
}

 

결과: 테스트설정

 

😮 왜 "공통설정"도 아니고 "개발설정"도 아닌 "테스트설정"이 출력됐을까?

  • 먼저 application.yml 로드 → app.name = 공통설정
  • 그다음 application-dev.yml 로드 → app.name = 개발설정 → 공통설정 덮어씌움
  • 그다음 application-test.yml 로드 → app.name = 테스트설정 → 다시 덮어씌움

결과적으로 가장 마지막에 우선순위가 높은 값이 적용돼서 "테스트설정"이 출력된 것이다.

이런식으로 스프링은 설정파일을 읽을 때 순서가 존재한다.

테스트를 실행할 때는 다음과 같은 순서로 설정 파일이 적용된다.

 

 

🔍 실제 로딩 순서

  • src/main/resources/application.yml: 공통 기본 설정 (우선순위 )
  • src/main/resources/application-dev.yml: @ActiveProfiles("dev")이므로 로드
  • src/test/resources/application-test.yml: 테스트 실행 시 자동 로드됨
  • @TestPropertySource, @SpringBootTest(properties = "..."): 가장 우선 적용 (우선순위 )

💡 src/test/resources/application-test.yml은 @ActiveProfiles("test")가 없어도 자동 적용됨

즉, 테스트용 설정은 항상 가장 강력하게 적용된다.


🚀 강제 우선순위 설정

@SpringBootTest(properties = {...}) 를 사용하면 모든 설정을 덮을 수 있다.

@SpringBootTest(properties = "app.name=강제 설정")
class OverridingTest {
    @Autowired
    Environment env;

    @Test
    void overrideTest() {
        System.out.println(env.getProperty("app.name")); // 강제 설정
    }
}
  • 테스트에서 원하는 값을 확실하게 덮고 싶다면 @SpringBootTest(properties = "...") 사용하자.

 

'Spring' 카테고리의 다른 글

[Spring] 단위 테스트 작성 with (JUnit5, Mockito)  (1) 2025.05.27
[Spring] BCryptPasswordEncoder  (0) 2025.04.17
[Spring] 스프링 빈과 스프링 컨테이너  (0) 2025.01.12
[Spring] 예외 처리 방식  (0) 2024.12.11
[Spring] Security JWT  (0) 2024.11.10