編寫自己的Spring-Boot的statrter

編寫自己的Spring-Boot的statrter

部分內容引用來源聲明:
 飛污熊博客 https://www.xncoding.com/2017/07/22/spring/sb-starter.html

  • 【概念理解】starter是一種服務——使得使用某個功能的開發者不需要關注各種依賴庫的處理,不需要具體的配置信息, 由Spring Boot自動通過classpath路徑下的類發現需要的Bean,並織入相應的Bean。舉個栗子,spring-boot-starter-jdbc這個starter的存在, 使得我們只需要在BookPubApplication下用@Autowired引入DataSource的bean就可以,Spring Boot會自動創建DataSource的實例。(記住啦,是一個服務,service, starter is a service)

  • 【關於配置的好習慣】
    @ConfigurationProperties註解的類會被spring-boot-configuration-processor檢測,spring-boot-configuration-processor 的作用是編譯時生成spring-configuration-metadata.json, 此文件主要給IDE使用,用於提示使用。如在intellij idea中,當配置此jar相關配置屬性在application.yml, 你可以用ctlr+鼠標左鍵,IDE會跳轉到你配置此屬性的類中。這個是附加功能,對starter的用戶友好。我爲人人,人人爲我。

  • 【關於命名】這裏說下artifactId的命名問題,Spring 官方 Starter通常命名爲spring-boot-starter-{name} 如 spring-boot-starter-web。Spring官方建議非官方Starter命名應遵循{name}-spring-boot-starter的格式。

  • 【要素】

    • 編寫service類實現,
    • 編寫ServiceProperties,要用@ConfigurationProperties註解聲明一下,這樣Spring就會根據註解讀取application.yml的配置,根據配置創建這個ServiceProperties的Bean實例。
    • 編寫AutoConfigure,用於控制Bean的初始化創建工作(這個類似編寫application-context.xml, 但是他比application多一個功能,那就是可以通過@Conditional這些條件註解,進行控制是否開啓。因爲Spring-Boot強調的是約定優先,事先約定條件,進行默認配置。不要動不動就得重新配置)
    • 在resources/META-INF/創建spring.factories文件,文件內容如下,由於SpringBoot啓動的時候不會掃描AutoConfigure類(Bean創建用的上下文),而是掃描所有Jar包的【resources/META-INF/】目錄,然後纔會加載AutoConfigure類,並初始化Service實例。
    org.springframework.boot.autoconfigure.EnableAutoConfiguration=com.xncoding.starter.config.ExampleAutoConfigure
    

完整代碼如下:


<dependencies>
        <!-- @ConfigurationProperties annotation processing (metadata for IDEs)
                 生成spring-configuration-metadata.json類,需要引入此類-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-configuration-processor</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-autoconfigure</artifactId>
        </dependency>
    </dependencies>


// 編寫服務類
public class ExampleService {

    private String prefix;
    private String suffix;

    public ExampleService(String prefix, String suffix) {
        this.prefix = prefix;
        this.suffix = suffix;
    }
    public String wrap(String word) {
        return prefix + word + suffix;
    }}
    
    
 // 編寫配置模板類
@ConfigurationProperties("example.service")
public class ExampleServiceProperties {
    private String prefix;
    private String suffix;

    public String getPrefix() {
        return prefix;
    }

    public void setPrefix(String prefix) {
        this.prefix = prefix;
    }

    public String getSuffix() {
        return suffix;
    }

    public void setSuffix(String suffix) {
        this.suffix = suffix;
    }
}

// 編寫Spring上下文類
@Configuration@ConditionalOnClass(ExampleService.class)@EnableConfigurationProperties(ExampleServiceProperties.class)public class ExampleAutoConfigure {

    private final ExampleServiceProperties properties;

    @Autowired
    public ExampleAutoConfigure(ExampleServiceProperties properties) {
        this.properties = properties;
    }

    @Bean
    @ConditionalOnMissingBean
    @ConditionalOnProperty(prefix = "example.service", value = "enabled",havingValue = "true")
    ExampleService exampleService (){
        return  new ExampleService(properties.getPrefix(),properties.getSuffix());
    }

}

// 添加meta文件到resources/META-INF/spring.factories

org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
com.xncoding.starter.config.ExampleAutoConfigure


// mvn:install 打包安裝


// 測試過程

// 引入starter
<dependency>
    <groupId>com.xncoding</groupId>
    <artifactId>simple-spring-boot-starter</artifactId>
    <version>1.0.0-SNAPSHOT</version>
 </dependency>
 

// 編寫 application.yml 配置
example.service:
  enabled: true
  prefix: ppp
  suffix: sss
 // main方法
 
@RunWith(SpringRunner.class)@SpringBootTestpublic class ApplicationTests {
    @Autowired
    private ExampleService exampleService;

    @Test
    public void testStarter() {
        System.out.println(exampleService.wrap("hello"));
    }
}
  
  
    
  • 【關鍵知識點,必看】@ConditionalOnMissingBean配置註解的類,可以被重寫(也就可以重新定義類的初始化,比如默認是單例的Bean可以改成多例,又或者默認的application.yml參數滿足你的需求,你也可以重新搞一個)
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章