2024. 11. 14. 20:08ㆍSpring Framework/Spring IoC
@Value
는 Spring에서 외부화된 속성 값을 주입하는 데 유용한 애노테이션입니다. @Value
를 통해 application.properties
또는 application.yml
파일의 값을 주입하거나, 스프링 표현 언어(SpEL)를 사용해 런타임 시 계산된 값을 주입할 수 있습니다. 다음은 @Value
의 다양한 활용 방법과 설정 방법에 대한 설명입니다.
1. 기본 사용법: 외부 속성 값 주입
@Value
애노테이션은 외부 속성을 주입하는 데 사용됩니다. 예를 들어, application.properties
파일에서 catalog.name
속성을 정의하고 이를 클래스에 주입할 수 있습니다.
# application.properties 파일
catalog.name=MovieCatalog
@Component
public class MovieRecommender {
private final String catalog;
// @Value를 사용해 catalog.name 속성 값을 주입
public MovieRecommender(@Value("${catalog.name}") String catalog) {
this.catalog = catalog;
}
}
위 코드에서 catalog
필드는 MovieCatalog
값으로 설정됩니다.
Java 기반 구성 메타데이터
외부 파일을 읽어올 수 있도록 @PropertySource
를 @Configuration
클래스에 추가해야 합니다.
@Configuration
@PropertySource("classpath:application.properties")
public class AppConfig { }
이렇게 하면 Spring이 application.properties
파일을 로드하고 @Value
에 정의된 속성 값을 주입할 수 있습니다.
2. 디폴트 값 설정
속성이 존재하지 않을 때 사용할 디폴트 값을 설정할 수도 있습니다.
@Component
public class MovieRecommender {
private final String catalog;
// catalog.name이 설정되지 않은 경우 defaultCatalog를 사용
public MovieRecommender(@Value("${catalog.name:defaultCatalog}") String catalog) {
this.catalog = catalog;
}
}
위 예제에서 catalog.name
속성이 정의되지 않았을 경우 catalog
필드는 defaultCatalog
값으로 설정됩니다.
3. 강력한 속성 해석을 위한 설정
Spring은 기본적으로 너그러운 속성 해석을 지원하여 속성 값을 찾지 못하면 ${catalog.name}
과 같은 원래의 속성 이름을 그대로 주입합니다. 그러나 존재하지 않는 값을 엄격하게 관리하려면 PropertySourcesPlaceholderConfigurer
빈을 설정하여 강력한 해석을 활성화할 수 있습니다.
@Configuration
public class AppConfig {
@Bean
public static PropertySourcesPlaceholderConfigurer propertyPlaceholderConfigurer() {
return new PropertySourcesPlaceholderConfigurer();
}
}
PropertySourcesPlaceholderConfigurer
를 설정하면, 속성 파일에서 ${}
플레이스홀더가 해석되지 않으면 Spring 초기화가 실패하게 됩니다. JavaConfig에서 PropertySourcesPlaceholderConfigurer
를 사용할 때는 @Bean
메서드를 static
으로 선언해야 합니다.
4. SpEL(Spring Expression Language) 사용
@Value
는 스프링 표현 언어(SpEL)를 사용하여 런타임 시 동적으로 값을 계산할 수도 있습니다. 예를 들어 시스템 속성을 기반으로 값을 생성할 수 있습니다.
@Component
public class MovieRecommender {
private final String catalog;
// SpEL 표현식 사용
public MovieRecommender(@Value("#{systemProperties['user.catalog'] + 'Catalog' }") String catalog) {
this.catalog = catalog;
}
}
위 예제에서 user.catalog
라는 시스템 속성의 값을 기반으로 catalog
필드에 값을 할당합니다.
5. 복잡한 데이터 구조 지원
SpEL을 사용하여 더 복잡한 데이터 구조도 주입할 수 있습니다. 예를 들어, Map
이나 List
와 같은 컬렉션을 생성하여 주입할 수 있습니다.
@Component
public class MovieRecommender {
private final Map<String, Integer> countOfMoviesPerCatalog;
// SpEL을 사용하여 Map 구조 주입
public MovieRecommender(
@Value("#{{'Thriller': 100, 'Comedy': 300}}") Map<String, Integer> countOfMoviesPerCatalog) {
this.countOfMoviesPerCatalog = countOfMoviesPerCatalog;
}
}
위 예제에서 countOfMoviesPerCatalog
필드는 {'Thriller': 100, 'Comedy': 300}
이라는 초기 값으로 설정됩니다.
6. ConversionService를 통한 타입 변환
Spring은 @Value
를 통해 주입된 값을 디폴트 타입 변환을 지원하여 Integer
나 int
로 자동 변환할 수 있습니다. 여러 개의 쉼표로 구분된 값은 자동으로 String
배열로 변환됩니다.
또한, 사용자 정의 타입 변환을 추가하고 싶다면 ConversionService
빈을 설정할 수 있습니다. 다음 예제에서는 사용자 정의 컨버터를 추가합니다.
@Configuration
public class AppConfig {
@Bean
public ConversionService conversionService() {
DefaultFormattingConversionService conversionService = new DefaultFormattingConversionService();
conversionService.addConverter(new MyCustomConverter()); // 사용자 정의 변환기 추가
return conversionService;
}
}
@Value
는 내부적으로 ConversionService
를 사용하여 문자열 값을 타겟 타입으로 변환합니다. MyCustomConverter
는 ConversionService
에서 사용할 사용자 정의 컨버터로, 필요한 경우 직접 작성할 수 있습니다.
7. Spring Boot의 디폴트 설정
Spring Boot는 디폴트로 PropertySourcesPlaceholderConfigurer
빈을 자동 구성하여 application.properties
와 application.yml
파일의 속성을 로드합니다. 별도로 PropertySourcesPlaceholderConfigurer
를 정의하지 않아도 Spring Boot는 이러한 속성 파일의 값을 자동으로 처리합니다.
요약
- @Value를 사용해 외부 속성이나 동적으로 계산된 값을 주입할 수 있습니다.
- 디폴트 값을 제공하거나 존재하지 않는 값을 엄격하게 관리할 수 있습니다.
- SpEL을 사용하여 동적 표현식이나 복잡한 데이터 구조를 주입할 수 있습니다.
- Spring의 디폴트 ConversionService를 통해 타입 변환을 지원하며, 사용자 정의 컨버터를 추가할 수 있습니다.
- Spring Boot에서는
application.properties
와application.yml
의 속성을 자동으로 처리하므로 추가 설정이 필요하지 않습니다.
이러한 @Value
의 기능을 통해 Spring 애플리케이션에서 외부화된 설정과 동적 값 주입이 보다 유연하게 가능합니다.
'Spring Framework > Spring IoC' 카테고리의 다른 글
Environment Abstraction (1) | 2024.11.14 |
---|---|
Using @PostConstruct and @PreDestory (0) | 2024.11.14 |
Injection with @Resource (0) | 2024.11.14 |
Using CustomAutowireConfigure (0) | 2024.11.14 |
Using Generics as Autowiring Qualifiers (0) | 2024.11.14 |