4

我试图弄清楚如何将属性文件的值放入我的 Spring Environment 属性中。

Spring 3.1 之前的做法是这样的:

  <context:property-placeholder location="classpath:my.properties" />

  <bean id="myBean" class="com.whatever.MyBean">
    <property name="someValue" value="${myProps.value}" />
    <!-- etc -->
  </bean>

我也可以这样做:

public class MyBean {

   @Value(value = "#{myProps.value}")
   private String someValue;

}

现在我表面上可以从 Environment 类中提取属性,与在我的 xml 或我的 bean 本身中使用笨拙的 #{myProps.value} 语法相比,这似乎是一种更简洁的获取属性的方法。

我在我的 XML 中试过这个:

<bean
    class="org.springframework.context.support.PropertySourcesPlaceholderConfigurer">
    <property name="location">
        <value>classpath:my.properties</value>
    </property>
</bean>

但是这些属性不会添加到环境中。

我知道我可以使用PropertySource属性,但我没有使用注释进行配置。

那么如何设置我的 bean / xml 以便在我的道具中设置的变量在环境中可用?此外,我怎样才能将这些值注入到我的 bean 中而不必明确地说“environmentInstance.getProperty(”myProps.value”)?

4

2 回答 2

1

For the web applications

If you want to have Environment populated before the XML bean definitions are processed, you should implement a ApplicationContextInitializer(), as described in the Spring Source blog

<context-param>
    <param-name>contextInitializerClasses</param-name>
    <param-value>com.bank.MyInitializer</param-value>
</context-param>

Here is a slightly modified version of the example from the blog

public class MyInitializer implements
        ApplicationContextInitializer<ConfigurableWebApplicationContext> {
    public void initialize(ConfigurableWebApplicationContext ctx) {
        ResourcePropertySource ps;
        try {
            ps = new ResourcePropertySource(new ClassPathResource(
                    "my.properties"));
        } catch (IOException e) {
            throw new AssertionError("Resources for my.properties not found.");
        }
        ctx.getEnvironment().getPropertySources().addFirst(ps);
    }
  }

For the standalone applications

Basically the same thing, you can modify the environment of the AbstractApplicationContext directly

   ResourcePropertySource ps;
   try {
        ps = new ResourcePropertySource(new ClassPathResource(
                        "my.properties"));
   }catch (IOException e) {
                throw new AssertionError("Resources for my.properties not found.");
   }
   //assuming that ctx is an AbstractApplicationContext
   ctx.getEnvironment().getPropertySources().addFirst(ps);

P.S. the earlier version of this answer showed an attempt to modify the Environment from the bean but it seems to be an antipattern spreading on SO, because for sure you would like to have Environment property sources list populated even before the XmlBeanDefinitionReader starts to process XML to make placeholders work inside the <import/> statement.

于 2013-01-08T21:59:56.740 回答
0

我的理解也有点混乱,但这是我能理解的:

  1. Environment 是一种指示当前活动配置文件的方法(而配置文件是一种有选择地创建 bean 的方法)
  2. PropertySources 可以与环境相关联,这样做的方法是使用 @PropertySource 注释,似乎没有等效的 xml 来执行此操作。
  3. 您的理解实际上应该是相反的,AFAIK:当您声明<context:property-placeholder占位符将根据本地声明的属性解析属性并且可以回退到环境中声明的属性源时,环境本身不会被新属性修改。同样,向环境本身添加属性的唯一方法似乎是通过 @PropertySource 注释
于 2013-01-08T21:57:48.263 回答