Properties@PropertySource@Value 를 통한 property value 주입Property Search HierarchyYaml로 프로퍼티 작성@ConfigurationProperties 로 property그룹 만들기Environment를 통한 Property 접근방법ProfileBean에 정의 (@Profile)property를 profile별로 작성하기(Spring Boot에서만 실습함)사용 시일반적 상황Spring boot Application 에서 사용시
EnvironmentCapable interface
- Bean들에게 영향을 주는 환경. Profile에 따라서 Property가 바뀌게 되는 것

var applicationContext = new AnnotationConfigApplicationConext(AppConfiguration.class); var environment = applicationContext.getEnvironment(); environment.getProperty("kdt.version"); // 이와 같은 방식으로 프로퍼티 접근이 가능함
Properties
- application.properties — Spring Boot에서 디폴트로 사용하는 프로퍼티 파일임.
- 기본 spring을 사용할 때에는 어떤 프로퍼티 파일을 사용해라 라고 알려주어야 함 (@Configuration 클래스에서
@PropertySource("application.properties")
)
- 프로퍼티 파일은 키 밸류 형태로 작성을 함
@PropertySource
- SpringBoot에서는 application.properties를 디폴트로 프로퍼티 파일로 사용하기에 따로 명시해주지 않아도 됨
- 그러나 기본 Spring에서는 어떤 프로퍼티 파일을 사용해라 라고 알려주어야 하는데 이것이 @PropertySource가 하는 역할임
@Value 를 통한 property value 주입
- @Value annotation 이용하면 property의 값을 컴포넌트나 다른 빈들에 주입할 수 있음
@Value(${property_name : default value})
형태로 property 값 적용 가능함
- 또한 시스템 환경변수의 값도 넣어줄 수 있음. property 와 시스템 환경변수의 이름이 동일하면 시스템 환경변수 값 우선임
- field값 말고 함수나 생성자의 인자로도 넣어줄 수 있음
//application.properties version= v1.0.0 kdt.version = v1.0.0 kdt.support-vendors = a, b, c, d, e, f, g kdt.minimum-order-amount = 1
@Component public class OrderProperties implements InitializingBean { @Value("${kdt.version:v0.0.0}") // kdt.version을 찾아보고 없으면 v0.0.0. // 이거 명시 안해주면 키 없으면 ${kdt.version}이게 그대로 들어가게 됨 private String version; @Value("${kdt.minimum-order-amount}") private int minimumOrderAmount; @Value("${kdt.support-vendors}") private List<String> supportVendors; @Value("${PATH}") private String path; // 시스템 환경 변수 값도 가져올 수 있음 @Override public void afterPropertiesSet() throws Exception { System.out.printf("version %s%n", version); System.out.printf("minimumOrderAmount %s%n", minimumOrderAmount); System.out.printf("supportVendors %s%n", supportVendors); } }
@Component @PropertySource("version.properties") public class VersionProvider{ private final String version; public VersionProvider(@Value("${version:v0.0.0}") String version){ this.version = version; } }
Property Search Hierarchy
- ServletConfig parameters
- ServletContext parameters
- JNDI environment variables
- JVM system properties ( -D commane-line arguments)
- JVM system environment (operating system environment variables)
Yaml로 프로퍼티 작성
kdt: version: "v1.0" minimum-order-amount: 1 support-vendors: - a - b - c - d description : |- line 1 hello world line2 xxxx line3
- array 는 - 로 쭉 아래로 나열 가능함
- 여러 줄을 쓰고 싶을 때에는 | 이 표시 이용. |- 로 표기하면 맨 마지막 줄에 줄바꿈이 있는걸 제외해 준다는 의미임
- @PropertySource 는 yaml 지원 안함
- Spring framework 에서는 PropertySourceFactory를 구현해야함. spring-boot에서는 지원함. 그 후
@PropertySource(value="application.yaml", factory= YamlPropertySourceFactory.class)
적용
public class YamlPropertySourceFactory implements PropertySourceFactory { @Override public PropertySource<?> createPropertySource(String name, EncodedResource resource) throws IOException { YamlPropertiesFactoryBean bean = new YamlPropertiesFactoryBean(); bean.setResources(resource.getResource()); var properties = bean.getObject(); return new PropertiesPropertySource(resource.getResource().getFilename(), properties); } }
@ConfigurationProperties 로 property그룹 만들기
- 스프링부트에서 외부 속성을 통해서 별도의 빈을 만들 수 있게 지원하는 어노테이션임
- 위에서의 @Value방식은 프로젝트가 작을 때에는 하나씩 할당 해 주어서 가능하지만, 전체적으로 매핑해서 그룹화해서 타입으로 사용하고 싶을 때는 @ConfigurationProperties를 이용함
- 그리고 위의 방법으로는 array에 대한 매핑이 안됨(support-vendors)
사용방식
- @ConfigurationProperties 붙여줌(해당 어노테이션은 spring boot용 이기 때문에
@EnableConfigurationProperties
어노테이션도 추가로 붙여주어야 함)
- yaml 파일의 이름과 똑같이 필드이름 만들어주고(이때, prefix부분 붙여주어야 함)
- gettter와 setter만들어주면 알아서 property값들이 매핑이 됨
@Configuration @ConfigurationProperties(prefix = "kdt") @PropertySource(value="application.yaml", factory = YamlPropertySourceFactory.class) @EnableConfigurationProperties public class Properties implements InitializingBean { public String getVersion() { return version; } public void setVersion(String version) { this.version = version; } public int getMinimumOrderAmount() { return minimumOrderAmount; } public void setMinimumOrderAmount(int minimumOrderAmount) { this.minimumOrderAmount = minimumOrderAmount; } public List<String> getSupportVendors() { return supportVendors; } public void setSupportVendors(List<String> supportVendors) { this.supportVendors = supportVendors; } public String getDescription() { return description; } public void setDescription(String description) { this.description = description; } private String version; private int minimumOrderAmount; private List<String> supportVendors; private String description; @Override public void afterPropertiesSet() throws Exception { System.out.println("version : " + version); System.out.println("minOrderAmount : " + minimumOrderAmount); System.out.println("list : " + supportVendors); System.out.println("description : " + description); } }
Environment를 통한 Property 접근방법
// 1. environment 얻어와서 거기서 property에 접근 var applicationContext = new AnnotationConfigApplicationConext(AppConfiguration.class); var environment = applicationContext.getEnvironment(); environment.getProperty("kdt.version"); // 이와 같은 방식으로 프로퍼티 접근이 가능함 // 2. ConfigurationProperties 클래스를 의존성 주입 받아서 property값들에 접근하기
Profile
Bean에 정의 (@Profile)
- local, dev, staging, production 등 이런 식으로 그룹화해서 profile을 만들어서 사용할 수 있음
- application 실행 시 그런 프로파일들 적용해서 실행되도록 할 수 있음
- Bean 정의하면서도 할 수 있고 stereotype annotation을 통해서도 할 수 있음
@Repository @Profile("dev") public class MemoryVoucherRepository implements VoucherRepository{ } @Repository @Profile("local") public class MemoryVoucherRepository implements VoucherRepository{ } AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(); context.register(AppConfig.class); var environment = context.getEnvironment(); environment.setActiveProfiles("dev"); context.refresh(); var voucherRepository = context.getBean(VoucherRepository.class); @Bean @Profile("dev") // 이런 방식으로
property를 profile별로 작성하기(Spring Boot에서만 실습함)
- 그러나 이 기능은 spring boot에서만 지원되는 기능임. spring boot application으로 실행해야 구분해서 property값 가져올 수 있음
spring.config.activate.on-profile: dev kdt: version: "v1.0" minimum-order-amount: 1 support-vendors: - a - b - c - d description : |- line 1 hello world line2 xxxx line3 --- // 이 부분 있어야함! 그래야 위 아래 구분이 됨 spring: config: activate: on-profile: local kdt: version: "v1.0" minimum-order-amount: 1 support-vendors: - dev-a - dev-b - c - d description : |- line 1 hello world line2 xxxx line3
- 위와 같이 한 파일에 작성할 수도 있고, application-dev.yaml, application-local.yaml 이런식으로 파일 따로 작성해도 됨. dev, local profile 알아서 읽어줌(Spring Boot에서)
- 이 때 application.yaml 파일은 profile 을 설정해주지 않았을때 읽게 되는 파일임. 만약 profile을 설정해 주지 않고 Bean들에
@Profile(”dev”)
@Profile(”local”)
이렇게만 설정해주게 되면, candidate bean이 없다는 에러가 발생함(”default”
도 추가해주어야..)
사용 시
일반적 상황
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(); context.register(AppConfig.class); var environment = context.getEnvironment(); environment.setActiveProfiles("local"); context.refresh(); System.out.println(context.getBean(Properties.class).getSupportVendors());
Spring boot Application 에서 사용시
SpringApplication springApplication = new SpringApplication(App.class); springApplication.setAdditionalProfiles("local"); var applicationContext = springApplication.run(args); var properties = applicationContext.getBean(Properties.class);
- SpringBootApplication인 경우에는 아래의 Edit Configuration에서도 Active profile 설정이 가능함
- 또는 Program arguments에
—spring.profiles.active=dev
와 같은 방식으로 명시해줌으로써 profile 설정도 가능