Spring Boot 推薦的基礎 POM 文件
Spring Boot 推薦的基礎 POM 文件
上一節的代碼清單 1 中給出的“org.springframework.boot:spring-boot-starter-web”是 Spring Boot 所提供的推薦的基礎 POM 文件之一,用來提供創建基於 Spring MVC 的 Web 應用所需的第三方庫依賴。除了這個 POM 文件之外,Spring Boot 還提供了其他類似的 POM 文件。所有這些基礎 POM 依賴都在“org.springframework.boot”組中。一些重要 POM 文件的具體說明見表 1。
表 1. Spring Boot 推薦的基礎 POM 文件
名稱 | 說明 |
---|---|
spring-boot-starter | 核心 POM,包含自動配置支持、日誌庫和對 YAML 配置文件的支持。 |
spring-boot-starter-amqp | 通過 spring-rabbit 支持 AMQP。 |
spring-boot-starter-aop | 包含 spring-aop 和 AspectJ 來支持麵向切麵編程(AOP)。 |
spring-boot-starter-batch | 支持 Spring Batch,包含 HSQLDB。 |
spring-boot-starter-data-jpa | 包含 spring-data-jpa、spring-orm 和 Hibernate 來支持 JPA。 |
spring-boot-starter-data-mongodb | 包含 spring-data-mongodb 來支持 MongoDB。 |
spring-boot-starter-data-rest | 通過 spring-data-rest-webmvc 支持以 REST 方式暴露 Spring Data 倉庫。 |
spring-boot-starter-jdbc | 支持使用 JDBC 訪問數據庫。 |
spring-boot-starter-security | 包含 spring-security。 |
spring-boot-starter-test | 包含常用的測試所需的依賴,如 JUnit、Hamcrest、Mockito 和 spring-test 等。 |
spring-boot-starter-velocity | 支持使用 Velocity 作為模板引擎。 |
spring-boot-starter-web | 支持 Web 應用開發,包含 Tomcat 和 spring-mvc。 |
spring-boot-starter-websocket | 支持使用 Tomcat 開發 WebSocket 應用。 |
spring-boot-starter-ws | 支持 Spring Web Services。 |
spring-boot-starter-actuator | 添加適用於生產環境的功能,如性能指標和監測等功能。 |
spring-boot-starter-remote-shell | 添加遠程 SSH 支持。 |
spring-boot-starter-jetty | 使用 Jetty 而不是默認的 Tomcat 作為應用服務器。 |
spring-boot-starter-log4j | 添加 Log4j 的支持。 |
spring-boot-starter-logging | 使用 Spring Boot 默認的日誌框架 Logback。 |
spring-boot-starter-tomcat | 使用 Spring Boot 默認的 Tomcat 作為應用服務器。 |
所有這些 POM 依賴的好處在於為開發 Spring 應用提供了一個良好的基礎。Spring Boot 所選擇的第三方庫是經過考慮的,是比較適合產品開發的選擇。但是 Spring Boot 也提供了不同的選項,比如日誌框架可以用 Logback 或 Log4j,應用服務器可以用 Tomcat 或 Jetty。
自動配置
Spring Boot 對於開發人員最大的好處在於可以對 Spring 應用進行自動配置。Spring Boot 會根據應用中聲明的第三方依賴來自動配置 Spring 框架,而不需要進行顯式的聲明。比如當聲明了對 HSQLDB 的依賴時,Spring Boot 會自動配置成使用 HSQLDB 進行數據庫操作。
Spring Boot 推薦采用基於 Java 注解的配置方式,而不是傳統的 XML。隻需要在主配置 Java 類上添加“@EnableAutoConfiguration”注解就可以啟用自動配置。Spring Boot 的自動配置功能是沒有侵入性的,隻是作為一種基本的默認實現。開發人員可以通過定義其他 bean 來替代自動配置所提供的功能。比如當應用中定義了自己的數據源 bean 時,自動配置所提供的 HSQLDB 就不會生效。這給予了開發人員很大的靈活性。既可以快速的創建一個可以立即運行的原型應用,又可以不斷的修改和調整以適應應用開發在不同階段的需要。可能在應用最開始的時候,嵌入式的內存數據庫(如 HSQLDB)就足夠了,在後期則需要換成 MySQL 等數據庫。Spring Boot 使得這樣的切換變得很簡單。
外部化的配置
在應用中管理配置並不是一個容易的任務,尤其是在應用需要部署到多個環境中時。通常會需要為每個環境提供一個對應的屬性文件,用來配置各自的數據庫連接信息、服務器信息和第三方服務賬號等。通常的應用部署會包含開發、測試和生產等若幹個環境。不同的環境之間的配置存在覆蓋關係。測試環境中的配置會覆蓋開發環境,而生產環境中的配置會覆蓋測試環境。Spring 框架本身提供了多種的方式來管理配置屬性文件。Spring 3.1 之前可以使用 PropertyPlaceholderConfigurer。Spring 3.1 引入了新的環境(Environment)和概要信息(Profile)API,是一種更加靈活的處理不同環境和配置文件的方式。不過 Spring 這些配置管理方式的問題在於選擇太多,讓開發人員無所適從。Spring Boot 提供了一種統一的方式來管理應用的配置,允許開發人員使用屬性文件、YAML 文件、環境變量和命令行參數來定義優先級不同的配置值。
Spring Boot 所提供的配置優先級順序比較複雜。按照優先級從高到低的順序,具體的列表如下所示。
- 命令行參數。
- 通過 System.getProperties() 獲取的 Java 係統參數。
- 操作係統環境變量。
- 從 java:comp/env 得到的 JNDI 屬性。
- 通過 RandomValuePropertySource 生成的“random.*”屬性。
- 應用 Jar 文件之外的屬性文件。
- 應用 Jar 文件內部的屬性文件。
- 在應用配置 Java 類(包含“@Configuration”注解的 Java 類)中通過“@PropertySource”注解聲明的屬性文件。
- 通過“SpringApplication.setDefaultProperties”聲明的默認屬性。
Spring Boot 的這個配置優先級看似複雜,其實是很合理的。比如命令行參數的優先級被設置為最高。這樣的好處是可以在測試或生產環境中快速地修改配置參數值,而不需要重新打包和部署應用。
SpringApplication 類默認會把以“--”開頭的命令行參數轉化成應用中可以使用的配置參數,如 “--name=Alex” 會設置配置參數 “name” 的值為 “Alex”。如果不需要這個功能,可以通過 “SpringApplication.setAddCommandLineProperties(false)” 禁用解析命令行參數。
RandomValuePropertySource 可以用來生成測試所需要的各種不同類型的隨機值,從而免去了在代碼中生成的麻煩。RandomValuePropertySource 可以生成數字和字符串。數字的類型包含 int 和 long,可以限定數字的大小範圍。以“random.”作為前綴的配置屬性名稱由 RandomValuePropertySource 來生成,如代碼清單 3 所示。
清單 3. 使用 RandomValuePropertySource 生成的配置屬性
1
2
3
4
5
|
user.id=${random.value} user.count=${random.int} user.max=${random.long} user.number=${random.int(100)} user.range=${random.int[100, 1000]} |
屬性文件
屬性文件是最常見的管理配置屬性的方式。Spring Boot 提供的 SpringApplication 類會搜索並加載 application.properties 文件來獲取配置屬性值。SpringApplication 類會在下麵位置搜索該文件。
- 當前目錄的“/config”子目錄。
- 當前目錄。
- classpath 中的“/config”包。
- classpath
上麵的順序也表示了該位置上包含的屬性文件的優先級。優先級按照從高到低的順序排列。可以通過“spring.config.name”配置屬性來指定不同的屬性文件名稱。也可以通過“spring.config.location”來添加額外的屬性文件的搜索路徑。如果應用中包含多個 profile,可以為每個 profile 定義各自的屬性文件,按照“application-{profile}”來命名。
對於配置屬性,可以在代碼中通過“@Value”來使用,如代碼清單 4 所示。
清單 4. 通過“@Value”來使用配置屬性
1
2
3
4
5
6
7
8
9
10
|
@RestController @EnableAutoConfiguration public class Application { @Value("${name}")
private String name;
@RequestMapping("/")
String home() {
return String.format("Hello %s!", name);
}
} |
在代碼清單 4 中,變量 name 的值來自配置屬性中的“name”屬性。
YAML
相對於屬性文件來說,YAML 是一個更好的配置文件格式。YAML 在 Ruby on Rails 中得到了很好的應用。SpringApplication 類也提供了對 YAML 配置文件的支持,隻需要添加對 SnakeYAML 的依賴即可。代碼清單 5 給出了 application.yml 文件的示例。
清單 5. 使用 YAML 表示的配置屬性
1
2
3
4
5
6
7
8
9
10
11
12
13
|
spring: profiles: development
db: url: jdbc:hsqldb:file:testdb
username: sa
password:
--- spring: profiles: test
db: url: jdbc:mysql://localhost/test
username: test
password: test
|
代碼清單 5 中的 YAML 文件同時給出了 development 和 test 兩個不同的 profile 的配置信息,這也是 YAML 文件相對於屬性文件的優勢之一。除了使用“@Value”注解綁定配置屬性值之外,還可以使用更加靈活的方式。代碼清單 6 給出的是使用代碼清單 5 中的 YAML 文件的 Java 類。通過“@ConfigurationProperties(prefix="db")”注解,配置屬性中以“db”為前綴的屬性值會被自動綁定到 Java 類中同名的域上,如 url 域的值會對應屬性“db.url”的值。隻需要在應用的配置類中添加“@EnableConfigurationProperties”注解就可以啟用該自動綁定功能。
清單 6. 使用 YAML 文件的 Java 類
1
2
3
4
5
6
7
|
@Component @ConfigurationProperties(prefix="db") public class DBSettings { private String url;
private String username;
private String password;
} |
開發 Web 應用
Spring Boot 非常適合於開發基於 Spring MVC 的 Web 應用。通過內嵌的 Tomcat 或 Jetty 服務器,可以簡化對 Web 應用的部署。Spring Boot 通過自動配置功能對 Spring MVC 應用做了一些基本的配置,使其更加適合一般 Web 應用的開發要求。
HttpMessageConverter
Spring MVC 中使用 HttpMessageConverter 接口來在 HTTP 請求和響應之間進行消息格式的轉換。默認情況下已經通過 Jackson 支持 JSON 和通過 JAXB 支持 XML 格式。可以通過創建自定義 HttpMessageConverters 的方式來添加其他的消息格式轉換實現。
靜態文件
默認情況下,Spring Boot 可以對 “/static”、“/public”、“/resources” 或 “/META-INF/resources” 目錄下的靜態文件提供支持。同時 Spring Boot 還支持 Webjars。路徑“/webjars/**”下的內容會由 webjar 格式的 Jar 包來提供。
生產環境運維支持
與開發和測試環境不同的是,當應用部署到生產環境時,需要各種運維相關的功能的支持,包括性能指標、運行信息和應用管理等。所有這些功能都有很多技術和開源庫可以實現。Spring Boot 對這些運維相關的功能進行了整合,形成了一個功能完備和可定製的功能集,稱之為 Actuator。隻需要在 POM 文件中增加對 “org.springframe.boot:spring-boot-starter-actuator” 的依賴就可以添加 Actuator。Actuator 在添加之後,會自動暴露一些 HTTP 服務來提供這些信息。這些 HTTP 服務的說明如表 2。
表 2. Spring Boot Actuator 所提供的 HTTP 服務
名稱 | 說明 | 是否包含敏感信息 |
---|---|---|
autoconfig | 顯示 Spring Boot 自動配置的信息。 | 是 |
beans | 顯示應用中包含的 Spring bean 的信息。 | 是 |
configprops | 顯示應用中的配置參數的實際值。 | 是 |
dump | 生成一個 thread dump。 | 是 |
env | 顯示從 ConfigurableEnvironment 得到的環境配置信息。 | 是 |
health | 顯示應用的健康狀態信息。 | 否 |
info | 顯示應用的基本信息。 | 否 |
metrics | 顯示應用的性能指標。 | 是 |
mappings | 顯示 Spring MVC 應用中通過“ @RequestMapping”添加的路徑映射。 |
是 |
shutdown | 關閉應用。 | 是 |
trace | 顯示應用相關的跟蹤(trace)信息。 | 是 |
對於表 2中的每個服務,通過訪問名稱對應的 URL 就可以獲取到相關的信息。如訪問“/info”就可以獲取到 info 服務對應的信息。服務是否包含敏感信息說明了該服務暴露出來的信息是否包含一些比較敏感的信息,從而確定是否需要添加相應的訪問控製,而不是對所有人都公開。所有的這些服務都是可以配置的,比如通過改變名稱來改變相應的 URL。下麵對幾個重要的服務進行介紹。
health 服務
Spring Boot 默認提供了對應用本身、關係數據庫連接、MongoDB、Redis 和 Rabbit MQ 的健康狀態的檢測功能。當應用中添加了 DataSource 類型的 bean 時,Spring Boot 會自動在 health 服務中暴露數據庫連接的信息。應用也可以提供自己的健康狀態信息,如代碼清單 7 所示。
清單 7. 自定義 health 服務
1
2
3
4
5
6
7
|
@Component public class AppHealthIndicator implements HealthIndicator { @Override
public Health health() {
return Health.up().build();
}
} |
應用隻需要實現 org.springframework.boot.actuate.health.HealthIndicator 接口,並返回一個 org.springframework.boot.actuate.health.Health 對象,就可以通過 health 服務來獲取所暴露的信息。如代碼清單 8 所示。
清單 8. health 服務返回的結果
1
|
{"status":"UP","app":{"status":"UP"},"db":{"status":"UP","database":"HSQL Database Engine","hello":1}} |
info 服務
info 服務所暴露的信息是完全由應用來確定的。應用中任何以“info.”開頭的配置參數會被自動的由 info 服務來暴露。隻需要往 application.properties 中添加以“info.”開頭的參數即可,如代碼清單 9 所示。
清單 9. 添加 info 服務所需配置參數的屬性文件
1
2
|
info.app_name=My First Spring Boot Application info.app_version=1.0.0 |
當訪問“/info”時,訪問的 JSON 數據如代碼清單 10 所示。
清單 10. Info 服務返回的結果
1
|
{"app_name":"My First Spring Boot Application","app_version":"1.0.0"} |
metrics 服務
當訪問 metrics 服務時,可以看到 Spring Boot 通過 SystemPublicMetrics 默認提供的一些係統的性能參數值,包括內存、CPU、Java 類加載和線程等的基本信息。應用可以記錄其他所需要的信息。Spring Boot 默認提供了兩種類型的性能指標記錄方式:gauge 和 counter。gauge 用來記錄單個絕對數值,counter 用來記錄增量或減量值。比如在一個 Web 應用中,可以用 counter 來記錄當前在線的用戶數量。當用戶登錄時,把 counter 的值加 1;當用戶退出時,把 counter 的值減 1。代碼清單 11 給出了一個示例。
清單 11. 自定義的 metrics 服務
1
2
3
4
5
6
7
8
9
10
|
@RestController public class GreetingsController { @Autowired
private CounterService counterService;
@RequestMapping("/greet")
public String greet() {
counterService.increment("myapp.greet.count");
return "Hello!";
}
} |
在代碼清單 11 中添加了對 Spring Boot 提供的 CounterService 的依賴。當 greet 方法被調用時,會把名稱為“myapp.greet.count”的計數器的值加 1。也就是當用戶每次訪問“/greet”時,該計算器就會被加 1。除了 CounterService 之外,還可以使用 GaugeService 來記錄絕對值。
使用 JMX 進行管理
添加 Actuator 後所暴露的 HTTP 服務隻能提供隻讀的信息。如果需要對應用在運行時進行管理,則需要用到 JMX。Spring Boot 默認提供了 JMX 管理的支持。隻需要通過 JDK 自帶的 JConsole 連接到應用的 JMX 服務器,就可以看到在域“org.springframework.boot”中 mbean。可以通過 Spring 提供的 @ManagedResource、@ManagedAttribute 和 @ManagedOperation 注解來創建應用自己的 mbean。
使用 Spring Boot CLI
Spring Boot 提供了命令行工具來運行 Groovy 文件。命令行工具的安裝非常簡單,隻需要下載之後解壓縮即可。下載地址見參考資源。解壓之後可以運行 spring 命令來使用該工具。通過 Groovy 開發的應用與使用 Java 並沒有差別,隻不過使用 Groovy 簡化的語法可以使得代碼更加簡單。代碼清單 12 給出了與代碼清單 2 功能相同的 Groovy 實現。
清單 12. 使用 Groovy 的示例應用
1
2
3
4
5
6
7
|
@RestController class WebApplication { @RequestMapping("/")
String home() {
"Hello World!"
}
} |
隻需要使用“spring run app.groovy”就可以運行該應用。還可以使用 Groovy 提供的 DSL 支持來簡化應用,如代碼清單 13 所示。
清單 13. 使用 Groovy DSL 簡化應用
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
|
@RestController class WebApplication { @Autowired
Service service
@RequestMapping("/")
String home() {
service.greet()
}
} class Service { String message String greet() {
message
}
} beans { service(Service) {
message = "Another Hello"
}
} |
在代碼清單 13 中,通過“beans”DSL 可以快速創建和配置 Spring bean。
結束語
對於廣大使用 Spring 框架的開發人員來說,Spring Boot 無疑是一個非常實用的工具。本文詳細介紹了如何通過 Spring Boot 快速創建 Spring 應用以及它所提供的自動配置和外部化配置的能力,同時還介紹了 Spring Boot 內建的 Actuator 提供的可以在生產環境中直接使用的性能指標、運行信息和應用管理等功能,最後介紹了 Spring Boot 命令行工具的使用。通過基於依賴的自動配置功能,使得 Spring 應用的配置變得非常簡單。在依賴的管理上也變得更加簡單,不需要開發人員自己來進行整合。Actuator 所提供的功能非常實用,對於在生產環境下對應用的監控和管理是大有好處的。Spring Boot 應該成為每個使用 Spring 框架的開發人員使用的工具。
最後更新:2017-08-13 22:50:44