속성 파일에서 목록을 읽고 스프링 주석 @Value로로드


244

.properties 파일에 값 목록을 갖고 싶습니다.

my.list.of.strings=ABC,CDE,EFG

그리고 내 수업에 직접로드하려면 :

@Value("${my.list.of.strings}")
private List<String> myList;

내가 이해하는 것처럼, 이것을 수행하는 대안은 그것을 스프링 설정 파일에 넣고 빈 참조로로드하는 것입니다 (잘못된 경우 수정하십시오).

<bean name="list">
 <list>
  <value>ABC</value>
  <value>CDE</value>
  <value>EFG</value>
 </list>
</bean>

그러나 이것을 수행하는 방법이 있습니까? .properties 파일을 사용합니까? 추신 : 가능한 경우 사용자 정의 코드 없이이 작업을 수행하고 싶습니다.

답변:


454

스프링 EL 사용하기 :

@Value("#{'${my.list.of.strings}'.split(',')}") 
private List<String> myList;

다음과 같이 특성 파일이 올바르게로드되었다고 가정하십시오.

my.list.of.strings=ABC,CDE,EFG

1
사용중인 것과 동일한 버전을 사용하여 다시 확인했습니다. 게시물과 마찬가지로 Spring EL을 복사하여 작동합니다. 다른 점은 EL에 오류가 발생하면 org.springframework.expression.spel.SpelEvaluationException예외가 아니라는 것 javax.el.ELException입니다. 당신의 반대는 Spring에 의해 만들어 졌습니까?
Wilhelm Kleu

1
Spring 3.2와 완벽하게 작동합니다.
ehsanullahjan

17
빈 속성은 my.list.of.strings=어떻습니까? 그런 기능이 빈 목록을 되풀이하여 여기에 하나의 항목 (빈 문자열)이 될 것이라고 기대하지 않습니까?
Jan Zyka

5
또한 제안 된 솔루션은 트리밍을하지 않으므로 같은 값을 item1, item2, item3사용하면 실제로 기대하지 않는 결과를 얻을 수 있습니다 (힌트 : 공백).
Jan Zyka

4
빈 공간을 @Value("#{'${my.list.of.strings}'.split(',\\s*')}")
다듬어야

88

Spring 3.0부터 다음과 같은 줄을 추가 할 수 있습니다

<bean id="conversionService" 
    class="org.springframework.context.support.ConversionServiceFactoryBean" />

당신 applicationContext.xml(또는 당신이 물건을 구성하는 곳)에. Dmitry Chornyi가 주석에서 지적한 것처럼 Java 기반 구성은 다음과 같습니다.

@Bean public ConversionService conversionService() {
    return new DefaultConversionService();
}

이것은 다음으로의 변환 String을 지원하는 새로운 구성 서비스를 활성화합니다Collection 유형 . 이 구성 서비스를 활성화하지 않으면 Spring은 레거시 속성 편집기를 구성 서비스로 대체하여 이러한 종류의 변환을 지원하지 않습니다.

다른 유형의 컬렉션으로 변환해도 작동합니다.

@Value("${my.list.of.ints}")
private List<Integer> myList

같은 라인으로 작동합니다

 my.list.of.ints= 1, 2, 3, 4

공백에는 문제가 없습니다. ConversionServiceFactoryBean 처리합니다.

참조 http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#core-convert-Spring-config를

Spring 애플리케이션에서는 일반적으로 Spring 컨테이너 (또는 ApplicationContext)마다 ConversionService 인스턴스를 구성합니다. 해당 ConversionService는 Spring에서 픽업 한 다음 프레임 워크에서 유형 변환을 수행해야 할 때마다 사용됩니다. [...] Spring에 ConversionService가 등록되어 있지 않으면 원래 PropertyEditor 기반 시스템이 사용됩니다.


6
자바 설정 : @Bean public ConversionService conversionService () {return new DefaultConversionService (); }
Dmitry Chornyi 2011

2
split()모든 표현에서 자신을 반복하지 않기 위해, 그것은 또한 당신에게주는 대신 빈 목록을 올바르게 처리합니다[null]
Didier L

속성이 재정의되면 작동하지 않습니다 (여러 속성 소스에 있음)
Daniel Hári

47

이 내용을 읽고 Spring Boot를 사용 하는 경우이 기능에 대한 추가 옵션이 1 개 있습니다

일반적으로 쉼표로 구분 된 목록은 실제 사용 사례에서 매우 어색합니다 (그리고 구성에서 쉼표를 사용하려는 경우 때로는 불가능합니다).

email.sendTo=somebody@example.com,somebody2@example.com,somebody3@example.com,.....

Spring Boot를 사용하면 다음과 같이 작성할 수 있습니다 (Index start at 0) :

email.sendTo[0]=somebody@example.com
email.sendTo[1]=somebody2@example.com
email.sendTo[2]=somebody3@example.com

다음과 같이 사용하십시오.

@Component
@ConfigurationProperties("email")
public class EmailProperties {

    private List<String> sendTo;

    public List<String> getSendTo() {
        return sendTo;
    }

    public void setSendTo(List<String> sendTo) {
        this.sendTo = sendTo;
    }

}


@Component
public class EmailModel {

  @Autowired
  private EmailProperties emailProperties;

  //Use the sendTo List by 
  //emailProperties.getSendTo()

}



@Configuration
public class YourConfiguration {
    @Bean
  public EmailProperties emailProperties(){
        return new EmailProperties();
  }

}


#Put this in src/main/resource/META-INF/spring.factories
  org.springframework.boot.autoconfigure.EnableAutoConfiguration=example.compackage.YourConfiguration

이스케이프 된 쉼표가 인식되지 않아서 여기에 설명 된 다른 솔루션이 작동하지 않는 문제가 있습니다. Spring 4 에서이 솔루션을 수행하는 방법이 있습니까?
sandrozbinden

34

my.list.of.strings=ABC,CDE,EFGin .properties 파일 을 지정하고

@Value("${my.list.of.strings}") private String[] myString;

문자열 배열을 얻을 수 있습니다. 를 사용 CollectionUtils.addAll(myList, myString)하면 문자열 목록을 얻을 수 있습니다.


나는 첫 번째 문자열 "ABC"얻을
오사마 Abdulsattar

19

@Autowired생성자 또는 세터 String.split()를 사용하고 본문 을 고려한 적이 있습니까?

class MyClass {
    private List<String> myList;

    @Autowired
    public MyClass(@Value("${my.list.of.strings}") final String strs) {
        myList = Arrays.asList(strs.split(","));
    }

    //or

    @Autowired
    public void setMyList(@Value("${my.list.of.strings}") final String strs) {
        myList = Arrays.asList(strs.split(","));
    }
}

내 코드의 테스트 가능성을 향상시키기 위해 다음 방법 중 하나로 자동 배선을 선호합니다.


14

Spring Boot 2를 사용하는 경우 추가 구성없이 그대로 작동합니다.

my.list.of.strings=ABC,CDE,EFG

@Value("${my.list.of.strings}")
private List<String> myList;

나를 위해 작동하지 않았으므로 위의 그림과 같이 Spring EL을 사용해야합니다.
Bilbo Baggins 2016 년

또는private List<String> myList;
Halayem Anis

예, 저에게도 효과가있었습니다. Spring Boot 2.2.6
Ankit

8

위의 모든 답변이 정확합니다. 그러나 한 줄로만 달성 할 수 있습니다. 다음 선언을 시도하면 쉼표로 구분 된 모든 값이 문자열 목록에 표시됩니다.

private @Value("#{T(java.util.Arrays).asList(projectProperties['my.list.of.strings'])}") List<String> myList;

또한 XML 구성에 다음 줄이 정의되어 있어야합니다.

<util:properties id="projectProperties" location="/project.properties"/>

속성 파일의 경로와 파일 이름을 바꾸십시오. 그리고 당신은 갈 수 있습니다. :)

이것이 도움이되기를 바랍니다. 건배.


1
이것은 나를 위해 일했지만 다음과 같은 주석을 표현해야했습니다.@Value("#{T(java.util.Arrays).asList('${my.list.of.strings}')}")
Steven

6

최신 Spring 프레임 워크 버전 (Spring 3.1 이상)을 사용하는 경우 SpringEL에서 문자열을 분리 할 필요가 없습니다.

Spring의 Configuration 클래스에 PropertySourcesPlaceholderConfigurer 및 DefaultConversionService를 간단히 추가하십시오 (예 : Configuration으로 주석이 달린 클래스).

@Configuration
public class AppConfiguration {

    @Bean
    public static PropertySourcesPlaceholderConfigurer propertyPlaceholderConfigurer() {
        return new PropertySourcesPlaceholderConfigurer();
    }

    @Bean public ConversionService conversionService() {
        return new DefaultConversionService();
    }
}

그리고 당신의 수업에서

@Value("${list}")
private List<String> list;

그리고 속성 파일에서

list=A,B,C,D,E

DefaultConversionService를 사용하지 않으면 필드에 값을 삽입 할 때 쉼표로 구분 된 String을 String 배열로 가져올 수 있지만 DefaultConversionService는 몇 가지 편리한 마술을 수행하고 Collection, Array 등에 값을 추가합니다. 그것에 대해 더 알고 싶습니다)

이 두 개를 사용하면 줄 바꿈을 포함한 모든 중복 공백을 처리 할 수 ​​있으므로 추가 논리를 추가하지 않아도됩니다.


이 구성을 추가하는 것이 작동하지만 이상한 일이 발생합니다. 파일 형식에 @Value를 사용할 수 없으므로 File with Resource를 변경해야합니다.
ad3luc

2

이 같은 주석 으로이 작업을 수행 할 수 있습니다

 @Value("#{T(java.util.Arrays).asList('${my.list.of.strings:a,b,c}')}") 
    private List<String> mylist;

여기에서 my.list.of.strings는 속성 파일에서 선택됩니다.없는 경우 기본값 a, b, c가 사용됩니다.

속성 파일에서 다음과 같은 것을 가질 수 있습니다

my.list.of.strings = d, e, f


2

값의 공백을주의하십시오. 나는 틀릴 수 있지만 쉼표로 구분 된 목록의 공백은 @Value와 Spel을 사용하여 잘리지 않는다고 생각합니다. 리스트

foobar=a, b, c

문자열 목록으로 읽습니다.

"a", " b", " c"

대부분의 경우 공백을 원하지 않을 것입니다!

표현식

@Value("#{'${foobar}'.trim().replaceAll(\"\\s*(?=,)|(?<=,)\\s*\", \"\").split(',')}")
private List<String> foobarList;

문자열 목록을 제공합니다.

"a", "b", "c".

정규식은 쉼표 바로 앞과 뒤에있는 모든 공백을 제거합니다. 값 내부의 공백은 제거되지 않습니다. 그래서

foobar = AA, B B, CCC

가치가 있어야한다

"AA", "B B", "CCC".

split () 메서드는 내부 정규 표현식을 구분 기호로 사용하므로 예제를 단순화 할 수 있습니다. <br/>@Value("#{'${foobar}'.trim().split( *, *)}")
Karlik_B

2

배열을 잡고 공간을 제거하는 것이 더 간단하다고 생각합니다.

@Value("#{'${my.array}'.replace(' ', '').split(',')}")
private List<String> array;

2

정수 목록의 경우 다음과 같이 작동합니다.

@Value("#{${my.list.of.integers}}")
private List<Integer> listOfIntegers;

특성 파일 :

my.list.of.integers={100,200,300,400,999}

또는 @Value ( "# {$ {my.set.of.integers}}") private Set <Integer> setOfIntegers;
Alexey Simonov

1

공통 구성 사용을 고려하십시오. 속성 파일의 항목을 배열 / 목록으로 나누는 기능이 내장되어 있습니다. SpEL 및 @Value와 결합하면 원하는 것을 제공해야합니다.


요청에 따라 여기에 필요한 것이 있습니다 (실제로 코드를 시도하지 않았고 오타가있을 수 있습니다).

Apache Commons Configuration에는 PropertiesConfiguration이 있습니다. 구분 된 문자열을 배열 / 목록으로 변환하는 기능을 지원합니다.

예를 들어, 특성 파일이있는 경우

#Foo.properties
foo=bar1, bar2, bar3

아래 코드로 :

PropertiesConfiguration config = new PropertiesConfiguration("Foo.properties");
String[] values = config.getStringArray("foo");

당신에게 문자열 배열을 줄 것입니다 ["bar1", "bar2", "bar3"]

Spring과 함께 사용하려면 앱 컨텍스트 XML에서 이것을 사용하십시오.

<bean id="fooConfig" class="org.apache.commons.configuration.PropertiesConfiguration">
    <constructor-arg type="java.lang.String" value="classpath:/Foo.properties"/>
</bean>

봄 콩에 이것을 넣으십시오.

public class SomeBean {

    @Value("fooConfig.getStringArray('foo')")
    private String[] fooArray;
}

나는 이것이 효과가 있다고 믿는다 : P


사용할 메소드와 클래스에 대해 더 구체적으로 설명하고 실제 샘플 코드 스 니펫이 좋을 것입니다.
JackDev

1

내가 선호하는 방법 (특히 문자열의 경우)은 다음과 같습니다.

admin.user={'Doe, John','Headroom, Max','Mouse, Micky'}

사용

@Value("#{${admin.user}}")
private List<String> userList;

이런 식으로 매개 변수에 쉼표도 포함 할 수 있습니다. 세트에도 적용됩니다.


0

속성 자리 표시자를 사용하는 경우 ser1702544 예제는

@Value("#{myConfigProperties['myproperty'].trim().replaceAll(\"\\s*(?=,)|(?<=,)\\s*\", \"\").split(',')}") 

자리 표시 자 xml 사용 :

<bean class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">   
    <property name="properties" ref="myConfigProperties" />
    <property name="placeholderPrefix"><value>$myConfigProperties{</value></property>
</bean>    

<bean id="myConfigProperties" class="org.springframework.beans.factory.config.PropertiesFactoryBean">
     <property name="locations">
         <list>
                <value>classpath:myprops.properties</value>
         </list>
     </property>
</bean> 

0

스프링 부트 2.2.6을 사용하고 있습니다.

내 속성 파일 :

usa.big.banks= JP Morgan, Wells Fargo, Citigroup, Morgan Stanley, Goldman Sachs

내 코드 :

@Value("${usa.big.banks}")
    private List<String> bigBanks;

@RequestMapping("/bigbanks")
    public String getBanks() {
        System.out.println("bigBanks = " + bigBanks);
        return bigBanks.toString();
    }

잘 작동합니다

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.