SpringBoot第三集:熱部署與單元測試(2021最新最易懂)
有興趣的可以先參考附錄簡單了解SpringBoot自動裝配流程。
一.SpringBoot開發熱部署
項目開發中,你是否也遇到更新配置文件信息后,必須重啟項目的,否則數據不更新的問題?
Spring Boot提供了一個名為spring-boot-devtools的模塊來使應用支持熱部署,提高開發效率,修改后無需手動重啟Spring Boot應用。使用也非常簡單,在pom.xmI中加入devtools的依賴就可以了。當然,首次引入后,項目應用需要重啟。否則不生效。
1 <!-- SpringBoot熱部署依賴 --> 2 <dependency> 3 <groupId>org.springframework.boot</groupId> 4 <artifactId>spring-boot-devtools</artifactId> 5 </dependency>
二.SprongBoot單元測試
對於java
開發者而言,Junit
應該無人不知了。所以SpringBoot
也是基於Junit
進行單位測試的。測試代碼位置:建議在:src/test/java目錄下
SpringBoot測試開發,只需要在pom中引入測試依賴即可使用,默認SpringBoot會排除低版本的Junit測試包。(SpringBoot推薦使用Junit5.x或更高版本)
JUnit中的注解測試常用注解:
@BeforeClass:針對所有測試,在每個類加載的開始和結束時運行,必須為靜態方法:static void
@Before:初始化方法,執行當前測試類的每個測試方法前執行。
@Test:測試方法,在這里可以測試期望異常和超時時間
@After:釋放資源,執行當前測試類的每個測試方法后執行
@AfterClass:針對所有測試,在每個類加載的開始和結束時運行,必須為靜態方法:static void
@Ignore:忽略的測試方法(只在測試類的時候生效,單獨執行該測試方法無效)基本不用
@RunWith:可以更改測試運行器 ,用來告訴JUnit不要使用內置的org.junit.runner.Runner進行單元測試,而應該使用指定的類做單元測試,對於Spring單元測試總是要使用 SpringRunner.class 。(一般不用)
一個單元測試類執行順序為:
@BeforeClass –> @Before –> @Test –> @After –> @AfterClass
每一個測試方法的調用順序為:
@Before –> @Test –> @After
1.測試案例
- 新建SpringBoot項目,默認會導入測試依賴,如果沒有請手動修改pom文件導入。
1 <!-- SpringBoot測試依賴 --> 2 <dependency> 3 <groupId>org.springframework.boot</groupId> 4 <artifactId>spring-boot-starter-test</artifactId> 5 <scope>test</scope> 6 <!-- 排除junit.vintage --> 7 <exclusions> 8 <exclusion> 9 <groupId>org.junit.vintage</groupId> 10 <artifactId>junit-vintage-engine</artifactId> 11 </exclusion> 12 </exclusions> 13 </dependency>
- 在src/test/java目錄下新建測試類。
@SpringBootTest注解是SpringBoot自1.4.0版本開始引入的一個用於測試的注解。
1 @SpringBootTest 2 class SpringBootApplicationTests { 3 4 @Autowired 5 IDCard idcard; 6 7 @Test 8 void contextLoads() { 9 System.out.println("測試:"+idcard); 10 } 11 12 }
- 選中測試方法名,右鍵執行Junit Test即可。
其他的測試注解:略。自行演示!
附錄
SpringBoot自動裝配原理分析,這里簡單將源碼摳出,可以自行理解(為便於注釋編輯)
Eclipse按住Ctrl見不松,鼠標左鍵點擊注解@SpringBootApplication,查看@SpringBootApplication注解源碼。
1 @Target(ElementType.TYPE) 2 @Retention(RetentionPolicy.RUNTIME) 3 @Documented 4 @Inherited 5 @SpringBootConfiguration // SpringBoot的基礎配置:其引入的注解類使用了注解@Configuration,實際就是將啟動類實現Spring管理 6 @EnableAutoConfiguration // 啟用自動裝配(自動配置) 進入看源碼 7 @ComponentScan(excludeFilters = { @Filter(type = FilterType.CUSTOM, classes = TypeExcludeFilter.class), 8 @Filter(type = FilterType.CUSTOM, classes = AutoConfigurationExcludeFilter.class) }) 9 public @interface SpringBootApplication {
1 @Target(ElementType.TYPE) 2 @Retention(RetentionPolicy.RUNTIME) 3 @Documented 4 @Inherited 5 @AutoConfigurationPackage // 自動配置注解包 6 @Import(AutoConfigurationImportSelector.class)// 導入自動裝配選擇器類(不是所有的信息都自動裝配的,不使用的內容,不應該加載,由這個類實現排除),繼續看源碼 7 public @interface EnableAutoConfiguration {
1 public class AutoConfigurationImportSelector implements DeferredImportSelector, BeanClassLoaderAware, 2 ResourceLoaderAware, BeanFactoryAware, EnvironmentAware, Ordered { 3 private static final AutoConfigurationEntry EMPTY_ENTRY = new AutoConfigurationEntry(); 4 // 省略其他方法等代碼 5 /** 6 * 該方法是一個獲取自動裝配項的方法,內部通過業務處理實現排除和選擇使用的自動裝配項 7 * @param annotationMetadata 是注解元數據(個人理解指的是應用中注解) 8 */ 9 protected AutoConfigurationEntry getAutoConfigurationEntry(AnnotationMetadata annotationMetadata) { 10 // 判斷:沒有/已啟用注解源數據 11 if (!isEnabled(annotationMetadata)) { 12 return EMPTY_ENTRY;// 沒有啟用則直接返回自動裝配配置對象(到此就止了) 13 } 14 // 獲取所有注解屬性 15 AnnotationAttributes attributes = getAttributes(annotationMetadata); 16 // 調用方法獲取所有可用配置:具體有那些可以看下一個方法 17 List<String> configurations = getCandidateConfigurations(annotationMetadata, attributes); 18 // 這個步驟實現了篩選重復的配置信息 19 configurations = removeDuplicates(configurations); 20 // 獲取所有需要排除的屬性集(沒有在項目中應用的) 21 Set<String> exclusions = getExclusions(annotationMetadata, attributes); 22 // 根據重復信息,和配出屬性集,檢查要排除的類 23 checkExcludedClasses(configurations, exclusions); 24 // 刪除所有需要排除的屬性集 25 configurations.removeAll(exclusions); 26 // 根據剩下的正確配置屬性集,獲取配置過濾器 27 configurations = getConfigurationClassFilter().filter(configurations); 28 // 啟動自動裝配的導入事件 29 fireAutoConfigurationImportEvents(configurations, exclusions); 30 // 返回所有自動配置項 31 return new AutoConfigurationEntry(configurations, exclusions); 32 } 33 34 // 省略其他方法等代碼 35 /** 36 * 該方法將根據注解源數據和注解屬性獲取所有默認可用的配置信息 37 */ 38 protected List<String> getCandidateConfigurations(AnnotationMetadata metadata, AnnotationAttributes attributes) { 39 // 讀取所有可用配置信息,從下面的一行代碼中可以看出它所加載讀取的文件 40 List<String> configurations = SpringFactoriesLoader.loadFactoryNames(getSpringFactoriesLoaderFactoryClass(), 41 getBeanClassLoader()); 42 // 判斷集合中是否為空,若為空,則說明沒有找到可用的自動配置信息(讀取的文件時META-INF/spring.factories。) 43 Assert.notEmpty(configurations, "No auto configuration classes found in META-INF/spring.factories. If you " 44 + "are using a custom packaging, make sure that file is correct."); 45 // 最后返回讀取的配置信息集合 46 return configurations; 47 }
Mavne找到Spring-Boot-autoconfigrue依賴,進入包META-INF打開文件:spring.factories
在上圖中,配置源會判斷是否啟用自動裝配,也只會加載已啟用的配置,只要我們在pom文件中引入的組件,SpringBoot都會幫我們自動配置。
可以通過在核心配置文件中添加如下代碼,實現控制台顯示配置詳情:
debug: true