Spring Boot實踐——用外部配置填充Bean屬性的幾種方法


引用:https://blog.csdn.net/qq_17586821/article/details/79802320

  spring boot允許我們把配置信息外部化。由此,我們就可以在不同的環境中使用同一套程序代碼。可以使用屬性文件,yaml文件,環境變量,命令行參數來實現配置信息的外部化。可以使用@Value注解來將屬性值直接注入到bean里邊。也可以使用@ConfigurationProperties注解將屬性值注入到結構化的對象里邊。

@ConfigurationProperties

  Spring boot 應用中,當使用注解方式定義一個Bean時,同時可以利用@ConfigurationProperties導入外部屬性填充到這個Bean的實例。本文通過例子介紹了幾種用法可以達到這種效果 :

  • @ConfigurationProperties + @Component 注解到bean定義類上
  • @ConfigurationProperties + @Bean注解在配置類的bean定義方法上
  • @ConfigurationProperties注解到普通類然后通過@EnableConfigurationProperties定義為bean

  例子所采用配置文件
        先在例子項目增加配置文件 src/main/resources/application.properties ,其內容如下

section1.name=Tom
section2.name=Jerry
section3.name=Dog

        方式1 : @ConfigurationProperties + @Component 注解到bean定義類上類定義為Bean

        // 將類定義為一個bean的注解,比如 @Component,@Service,@Controller,@Repository
        // 或者 @Configuration
        @Component
        // 表示使用配置文件中前綴為 section1 的屬性的值初始化該bean定義產生的的bean實例的同名屬性
        // 在使用時這個定義產生的bean時,其屬性 name 會是 Tom
        @ConfigurationProperties(prefix = "section1")
        public class Bean1 {
            public String getName() {
                return name;
            }

            public void setName(String name) {
                this.name = name;
            }
            
            private String name;
        }

        方式2 : @ConfigurationProperties + @Bean注解在配置類的bean定義方法上Bean來自一個普通類

        // 這是一個一般java類,POJO,沒有任何注解
        public class Bean2 {
            public String getName() {
                return name;
            }

            public void setName(String name) {
                this.name = name;
            }

            private String name;
        }

  使用@Bean注解將一個配置類的方法定義為一個bean
        在項目的某個@Configuration配置類中通過@Bean注解在某個方法上將上面的POJO類定義為一個bean,並使用配置文件中相應的屬性初始化該bean的屬性。
        這里所說的@Configuration配置類可以是直接通過@Configuration注解的配置類,也可以是隱含使用了@Configuration注解的類,比如下面的例子中,@SpringBootApplication隱含了@Configuration。

        // 聲明為Spring boot 應用,隱含了注解@Configuration
        @SpringBootApplication
        public class Application {
            // @Bean 注解在該方法上定義一個bean,這種基於方法的Bean定義不一定非要出現在
            // @SpringBootApplication 注解的類中,而是出現在任何@Configuration注解了
            // 的類中都可以
            @Bean
            // 使用配置文件中前綴為section2的屬性的值初始化這里bean定義所產生的bean實例的同名屬性,
            // 在使用時這個定義產生的bean時,其屬性 name 會是 Jerry
            @ConfigurationProperties(prefix = "section2")
            public Bean2 bean2() {
                // 注意,這里的 Bean2 是上面所示的一個POJO類,沒有任何注解
                return new Bean2();
            }

            public static void main(String[] args) throws Exception {
                SpringApplication.run(Application.class, args);
            }
        }

        方式3 : @ConfigurationProperties注解到普通類然后通過@EnableConfigurationProperties定義為bean

  注解一個普通類的屬性將會來自外部屬性文件

        // 該注解聲明如果該類被定義為一個bean,則對應的bean實例的屬性值將來自配置文件中前綴為
        // section3的同名屬性。但是這個注解本身並不會導致該類被作為一個bean注冊
        @ConfigurationProperties(prefix = "section3")
        public class Bean3 {
            public String getName() {
                return name;
            }

            public void setName(String name) {
                this.name = name;
            }

            private String name;
        }

        使用@EnableConfigurationProperties將上述類定義為一個bean

        @SpringBootApplication
        // 該注解會將類Bean3作為一個bean定義注冊到bean容器,而類Bean3上的注解
        // @ConfigurationProperties(prefix = "section3")會導致目標bean
        // 實例的屬性值使用配置文件中前綴為section3的同名屬性值來填充,也就是目標
        // bean的屬性name的值會是Dog
        @EnableConfigurationProperties({Bean3.class})
        public class Application {
            public static void main(String[] args) throws Exception {
                SpringApplication.run(Application.class, args);
            }
        }

 

注意重點:

  • 使用@ConfigurationProperties,在這種綁定中,getter 和 setter 方法是強制的,因為這里的綁定是通過標准的Java Bean屬性綁定,但是也有例外。
  • 屬性配置類的屬性名和配置文件中配置信息是對應的(這里的對應並不是要求一模一樣,只要能轉換成功,就算對應,比如下划線語法、駝峰語法等都能接受)

 

@Value

  • @Value+ @Component 注解到bean定義類上
  • @Value+ @Bean注解在配置類的bean定義方法上

實現方式同上只是要寫全對應的名

  配置文件

book.author=onlymate
book.name=Java is s magic

對應的bean

@Bean
//@Component
@PropertySource("classpath:files/el.properties")
public class CustomElConfig {
    //注入普通字符串
    @Value("I Love YOU!")
    private String normal;
    //注入操作系統屬性
    @Value("#{systemProperties['os.name']}")
    private String osName;
    //注入表達式結果
    @Value("#{T(java.lang.Math).random()*100.0}")
    private double randomNumber;
    //注入其他的bean屬性
    @Value("#{customElBean.another}")
    private String fromAnother;
    //注入文件資源
    @Value("classpath:files/test.txt")
    private Resource testFile;
    //注入網址資源
    @Value("http://www.baidu.com")
    private Resource testUrl;
    //注入配置文件
    @Value("${book.name}")
    private String bookNmame;
    @Value("${book.author}")
    private String bookAuthor;
    //注入環境
    @Autowired
    private Environment environment;
    
    @Bean
    public static PropertySourcesPlaceholderConfigurer propertyConfigure(){
        return new PropertySourcesPlaceholderConfigurer();
    }
    
    public void outputResource(){
        try {
            System.out.println(normal);
            System.out.println(osName);
            System.out.println(randomNumber);
            System.out.println(fromAnother);
            System.out.println(IOUtils.toString(testFile.getInputStream(), Charset.defaultCharset()));
            System.out.println(IOUtils.toString(testUrl.getInputStream(), Charset.defaultCharset()));
            System.out.println(bookNmame);
            System.out.println(environment.getProperty("book.author"));
 
        }catch (Exception e){
            e.printStackTrace();
            System.out.println(e);
        }
    }

}

這里不需要寫出set、get方法,屬性名也任意,只要@Value("${book.author}")里面的key要對應配置文件中的key

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM