spring-boot-starter的關鍵、編寫示例

筆者語錄 話不多說,直接開幹。


spring-boot-starter的關鍵

@SpringBootApplication註解源碼是這樣的:
在這裏插入圖片描述
  @ComponentScan註解的作用是把(@SpringBootApplication所在的)入口類所在的包(及其子包)下的所有被@Component註解(或拓展了@Component的註解)標記了的bean註冊到spring容器中。那麼,處於@ComponentScan掃描範圍外的bean是如何註冊到容器中的呢,那就是靠@EnableAutoConfiguration來實現註冊的
  @EnableAutoConfiguration註解的作用是:將普通jar包資源目錄下的META-INF/spring.factories文件裏面配置的鍵爲org.springframework.boot.autoconfigure.EnableAutoConfiguration的類納入考慮範圍內,考慮是否將這個(些)類註冊進Spring容器。如果這個(些)類被@Component註解(或拓展了@Component的註解)標記了,且滿足@Conditional…條件(如果有@Conditional…的話),那麼將其註冊進Spring容器,如果不滿足條件,那麼就不註冊進Spring容器。
在這裏插入圖片描述

  • 注:追蹤源碼可知,在@EnableAutoConfiguration註解裏面啓用了SpringBoot的AutoConfigurationImportSelector類, 在AutoConfigurationImportSelector類中的getAutoConfigurationEntry方法裏,調用了Spring的SpringFactoriesLoader#loadFactories來加載資源jar包下的META-INF/spring.factories文件裏的key爲org.springframework.boot.autoconfigure.EnableAutoConfiguration的value集合
  • 注:@Conditional…條件有:
    在這裏插入圖片描述

編寫spring-boot-starter(示例)

提示 artifactId的命名需要注意,spring-boot-starter-xxx是SpringBoot官方保留的starter命名方式;業界自定義的starter的命名,一般用xxx-spring-boot-starter

第一步創建一個SpringBoot項目,並簡單改造

  1. 在pom.xml中引入spring-boot-configuration-processor和spring-boot-autoconfigure(完整pom.xml見下方)。
  2. 去掉pom.xml中的打可執行的jar包的插件(完整pom.xml見下方)。在這裏插入圖片描述
    注:普通的jar包與可執行的jar包的class文件路徑是不一樣的。
    注:只要去掉這個打包插件就行;去不去掉SpringBoot的啓動類都沒關係,不過出於潔癖考慮,推薦同時去掉啓動類。
    注:這裏 給出完整的pom.xml:
    <?xml version="1.0" encoding="UTF-8"?>
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
             xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
        <modelVersion>4.0.0</modelVersion>
        <parent>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-parent</artifactId>
            <version>2.2.6.RELEASE</version>
            <relativePath/> <!-- lookup parent from repository -->
        </parent>
        <groupId>com.pingan</groupId>
        <artifactId>custom-spring-boot-starter</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <name>custom-spring-boot-starter</name>
        <description>編寫spring-boot-starter</description>
    
        <properties>
            <java.version>1.8</java.version>
        </properties>
    
        <dependencies>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter</artifactId>
            </dependency>
    
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-test</artifactId>
                <scope>test</scope>
                <exclusions>
                    <exclusion>
                        <groupId>org.junit.vintage</groupId>
                        <artifactId>junit-vintage-engine</artifactId>
                    </exclusion>
                </exclusions>
            </dependency>
    
            <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>
    
            <dependency>
                <groupId>org.projectlombok</groupId>
                <artifactId>lombok</artifactId>
                <optional>true</optional>
            </dependency>
        </dependencies>
    
    </project>
    

第二步編寫“管理”類。這個類用來管理:啓用哪些被@ConfigurationProperties標記了的類、註冊哪些Bean等等

import com.pingan.customstarter.service.LogicHandler;
import lombok.Getter;
import lombok.Setter;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

/**
 * starter管理類
 *
 * @author JustryDeng
 * @date 2020/4/4 14:48:27
 */
@Configuration
@EnableConfigurationProperties(CustomAutoConfiguration.Properties.class)
@ConditionalOnProperty(value = "coder.info.enabled", havingValue = "true")
public class CustomAutoConfiguration {

    @Bean
    public LogicHandler logicHandler() {
        return new LogicHandler();
    }

    /**
     * 配置信息
     *
     * @author JustryDeng
     * @date 2020/4/4 14:38:05
     */
    @Setter
    @Getter
    @ConfigurationProperties(prefix = "coder.info")
    public static class Properties {

        /** 是否啓用 */
        private boolean enabled = false;

        /** 姓名 */
        private String name;

        /** 愛好 */
        private String motto;
    }
}

注:這個管理類不是必須的。如果不創建這個管理類來統一管理那些可能需要註冊進容器的類的話,那麼就需要在第四步(見下文)的spring.factories文件裏,指定這些類了;無疑,創建管理類更方便,更利於維護。

第三步編寫一個業務邏輯相關的類(見:第二步註冊進Spring的那個bean),用來做需要的邏輯在這裏插入圖片描述

第四步在資源目錄下的META-INF/spring.factories文件(無則創建)裏,通過org.springframework.boot.autoconfigure.EnableAutoConfiguration指定要註冊進容器的類

注:指定後,這個類不是說一定會被註冊進容器,其必須被@Component註解(或拓展了@Component的註解)標記了,並且如果其有@Conditional…條件的話,那麼還需要滿足條件,纔會被註冊進Spring容器。
注:如果需要註冊多個類,那麼使用逗號隔開,如:在這裏插入圖片描述

第五步mvn install到本地倉庫(,mvn deploy到遠程倉庫),供其它項目使用


測試一下

  • 第一步: 創建一個新的SpringBoot項目,並在pom.xml中,引入我們編寫的starter。在這裏插入圖片描述
  • 第二步: 在application.yml中配置參數,使觸發啓動starter中的配置類。在這裏插入圖片描述
  • 第三步: 編寫測試代碼,並測試。
    在這裏插入圖片描述
  • 啓動項目,控制檯輸出:
    在這裏插入圖片描述

由此可見,自定義spring-boot-starter成功!


^_^ 如有不當之處,歡迎指正

^_^ 參考鏈接
                       https://www.cnblogs.com/yuansc/p/9088212.html
                       https://www.cnblogs.com/softidea/p/6886460.html

                       https://blog.csdn.net/SkyeBeFreeman/article…

^_^ 參考資料
        《Spring Boot Cookbook》

^_^ 測試代碼託管鏈接
         https://github.com/JustryDeng/…spring-boot-starter…

^_^ 本文已經被收錄進《程序員成長筆記(二)》,筆者JustryDeng

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章