1. 程式人生 > >Spring Boot快速上手

Spring Boot快速上手

Spring Boot簡介

Spring Boot是由Pivotal團隊提供的全新框架,其設計目的是用來簡化新Spring應用的初始搭建以及開發過程。有了它,你可以更加敏捷地開發Spring應用程式,專注於應用程式的功能,而不用在Spring的配置上多花功夫,甚至完全不用配置。

Spring Boot提供了四個核心功能:

  • 自動配置:針對很多Spring應用程式的常見的應用功能,Spring Boot能自動提供相關的配置;
  • 起步依賴:告訴Spring Boot需要什麼功能,它就能引入需要的庫;
  • Spring Boot CLI:你只需寫程式碼就能完成完整的應用程式,無需傳統專案構建;
  • Actuator:讓你深入執行中的Spring Boot應用程式,一探究竟。

每一個特性都能以自己的方式簡化Spring應用的開發。

首先,我們看一下如何開發一個Spring Boot的Hello World程式。

Spring Boot工程搭建

Spring Boot工程與普通的maven/gradle工程無異,只是在依賴中需要新增對Spring Boot的依賴。不過,有一種更簡單的方式是直接用Spring官網的Spring Initializer來生成專案骨架。

開啟:https://start.spring.io/,填寫工程型別、語言、Spring Boot版本號及構件資訊,如下圖:

點選Generate Project後,會自動下載完整的專案骨架下來,並且在pom.xml中已經幫你依賴好了所需依賴的構件。

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 http://maven.apache.org/xsd/maven-4.0.0.xsd">
	<modelVersion>4.0.0</modelVersion>

	<groupId>com.example</groupId>
	<artifactId>demo</artifactId>
	<version>0.0.1-SNAPSHOT</version>
	<packaging>jar</packaging>

	<name>demo</name>
	<description>Demo project for Spring Boot</description>

	<parent>
		<groupId>org.springframework.boot</groupId>
		<artifactId>spring-boot-starter-parent</artifactId>
		<version>2.1.0.RELEASE</version>
		<relativePath/> <!-- lookup parent from repository -->
	</parent>

	<properties>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
		<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
		<java.version>1.8</java.version>
	</properties>

	<dependencies>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-web</artifactId>
		</dependency>

		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-test</artifactId>
			<scope>test</scope>
		</dependency>
	</dependencies>

	<build>
		<plugins>
			<plugin>
				<groupId>org.springframework.boot</groupId>
				<artifactId>spring-boot-maven-plugin</artifactId>
			</plugin>
		</plugins>
	</build>


</project>

同時可以看到主類DemoApplication.java:

package com.example.demo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class DemoApplication {

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

執行該類,看到如下輸出即為啟動成功:

至此,我們便完成了一個最簡專案的搭建和執行。

Spring Boot應用的啟動流程

DemoApplication類在我們的Spring Boot應用中有兩個作用:配置和啟動引導。

我們可以看到在主類上,有一個@SpringBootApplication註解,這個註解開啟了Spring的元件掃描和Spring Boot的自動配置功能,檢視其原始碼:

//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by Fernflower decompiler)
//

package org.springframework.boot.autoconfigure;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.context.TypeExcludeFilter;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.FilterType;
import org.springframework.context.annotation.ComponentScan.Filter;
import org.springframework.core.annotation.AliasFor;

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan(
    excludeFilters = {@Filter(
    type = FilterType.CUSTOM,
    classes = {TypeExcludeFilter.class}
), @Filter(
    type = FilterType.CUSTOM,
    classes = {AutoConfigurationExcludeFilter.class}
)}
)
public @interface SpringBootApplication {
    @AliasFor(
        annotation = EnableAutoConfiguration.class
    )
    Class<?>[] exclude() default {};

    @AliasFor(
        annotation = EnableAutoConfiguration.class
    )
    String[] excludeName() default {};

    @AliasFor(
        annotation = ComponentScan.class,
        attribute = "basePackages"
    )
    String[] scanBasePackages() default {};

    @AliasFor(
        annotation = ComponentScan.class,
        attribute = "basePackageClasses"
    )
    Class<?>[] scanBasePackageClasses() default {};
}

可以看到它是把Spring的@Configuration、Spring的@ComponentScan和Spring Boot的@EnableAutoConfiguration組合到了一起。

Spring Boot起步依賴

在傳統的Spring應用中,使用某個特定的功能時,需要自己手動新增對應的依賴,不僅麻煩,而且容易因為不同構件版本之間的相容問題而出錯。

Spring Boot提供了眾多的起步依賴,降低專案依賴的複雜度。起步依賴本質上是一個Maven專案物件模型,定義了對其他庫的傳遞依賴,這些東西加在一起即支援某項功能。

在上面的例子中,期望開發一個Web應用,我們依賴了spring-boot-starter-web,由它去依賴其他的構件。

Spring Boot自動配置

Spring Boot自動配置是一個執行時(更準確地說,是應用程式啟動時)的過程,考慮了眾多因素,才決定Spring配置應該用哪個,不該用哪個。

例如:Spring的JdbcTemplate是不是在Classpath下?如果是,並且有DataSource Bean,那麼就自動配置一個JdbcTemplate的Bean等等。

自動配置的原理是利用了Spring4.0引入的條件化配置的特性,條件化配置允許配置存在於應用程式中,但在滿足特定的條件之前都忽略這些配置。

以Spring Boot下的國際化為例,其自動配置類在org.springframework.boot.autoconfigure.context.MessageSourceAutoConfiguration類中。大致原始碼如下:

package org.springframework.boot.autoconfigure.context;

@Configuration
@ConditionalOnMissingBean(
    value = {MessageSource.class},
    search = SearchStrategy.CURRENT
)
@AutoConfigureOrder(-2147483648)
@Conditional({MessageSourceAutoConfiguration.ResourceBundleCondition.class})
@EnableConfigurationProperties
public class MessageSourceAutoConfiguration {
    private static final Resource[] NO_RESOURCES = new Resource[0];

    public MessageSourceAutoConfiguration() {
    }

    @Bean
    @ConfigurationProperties(
        prefix = "spring.messages"
    )
    public MessageSourceProperties messageSourceProperties() {
        return new MessageSourceProperties();
    }

    @Bean
    public MessageSource messageSource(MessageSourceProperties properties) {
    ...

可以看到這個配置類上使用了條件化註解@ConditionalOnMissingBean(value = MessageSource.class, search = SearchStrategy.CURRENT),表示在當前上下文中不存在MessageSource Bean時,這個配置類才生效。然後根據其messageSource(MessageSourceProperties)方法,自動建立一個MessageSource Bean。

Spring Boot應用的打包和執行

Spring Boot應用可以被打包成jar檔案直接執行,如果是Web應用,也可以打包成war包丟進傳統的應用伺服器(如Tomcat等)中執行。由於Spring Boot在應用程式裡嵌入了一個Servlet容器,所以Spring Boot開發的Web應用也可以打包成jar包直接執行,而不用部署到傳統的Java應用伺服器裡。

舉一個Spring Boot開發RESTful介面的例子:

在前面我們建立好的工程中,加入一個RestController如下:

package com.example.demo;

import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import java.util.HashMap;
import java.util.Map;

@RestController
public class DemoService {

    @RequestMapping(method = RequestMethod.POST, path = "/rest/evaluate")
    public Map<String, Object> query(@RequestBody Map<String, Object> params) {
        Map<String, Object> obj = new HashMap<String, Object>(5) {
            {
                put("price", 19.25);
                put("amount", 17891);
                put("commodity", "iPhone X");
            }
        };
        return obj;
    }
}

然後我們對工程執行mvn clean package,打出jar包,然後通過java命令執行起該jar包,通過postman訪問本地8080埠:

可以訪問成功。

在我們的pom.xml中,可以看到使用了外掛spring-boot-maven-plugin,這個外掛的作用是在打jar包時打出一個超級jar,把應用程式所有依賴都打進這個jar中,同時為jar新增一個描述檔案,其中的內容能讓你用java -jar執行應用程式。我們開啟jar包的BOOT-INF/lib目錄,可以看到依賴的jar包都被打進來了:

至此,我們完成了對Spring Boot的一個概要的瞭解,掌握瞭如何建立Spring Boot應用,Spring Boot的核心特性以及如何打包部署執行Spring Boot程式。快去開發你的Spring Boot應用吧~~