Spring Boot學習筆記01--基本介紹

摘要

看完本文你將掌握如下知識點:

  1. 如何搭建一個SpringBoot項目
  2. SpringBoot自動配置原理
  3. SpringBoot屬性配置方法
  4. 修改默認的Logback日志為log4j和log4j2的方法
  5. 修改默認的內置tomcat容器為Jetty容器和Undertow容器的方法
  6. SpringBoot單元測試方法
  7. 使用war包運行項目

SpringBoot系列Spring Boot學習筆記


Spring Boot簡介

  • 要我給Spring Boot做個定義,簡單來說就是一個基于強大的Spring框架的、推崇JavaConfig的極簡配置的web開發框架;
  • Spring Boot通過內嵌Servlet容器(Tomcat、Jetty,等等)的方式,可以以jar包的形式獨立運行一個web項目;
  • Spring Boot提倡JavaConfig和注解的零配置方式,并且默認配置滿足絕大多數場景的需要,意味著少量修改默認配置即可快速搭建一個web項目,極大的提高開發效率;
  • 項目中加入某一個spring-boot-starter-*依賴,就可以引入該功能的完整jar包,降低pom的復雜度
  • 本文基于Spring Boot的版本為1.4.2.RELEASE

Spring Boot項目創建方法

  • http://start.spring.io:可以通過網頁創建項目結構并下載;
  • Spring Boot CLI:通過命令行的方式創建Spring Boot項目;
  • Spring Tool Suite:習慣Eclipse的用戶可以使用STS創建『Spring Starter Project』項目;
  • IntelliJ IDEA:強大的生產力工具,推薦使用,創建『Spring Initializr』項目;

使用IntelliJ IDEA創建一個web項目

  1. 新建Spring Initializr項目


說明:Spring Boot要求JDK1.6+

  1. 填寫項目信息,構建工具使用maven


  2. 選擇項目使用的依賴,這里我們只需要勾選web


  1. Spring Boot當前最新的穩定版是1.4.2;
  2. 所有依賴可以在創建時勾選,也可以在創建后手工將依賴添加到pom中,如果對依賴比較熟悉,推薦手工添加,這樣可以加快創建項目的時間;
  1. 填寫項目名稱,點擊Finish


  2. 新建的項目結構如下


SpringBoot項目只會在項目根目錄下生成一個類--SpringBootWebDemoApplication(artifactId+Application),它就是一個帶有main函數的啟動類;

package com.example;

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

@SpringBootApplication
public class SpringBootWebDemoApplication {

    public static void main(String[] args) {
        SpringApplication.run(SpringBootWebDemoApplication.class, args);
    }
}
  • 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>springbootwebdemo</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <packaging>jar</packaging>

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

  <!-- 創建的Springboot項目需要繼承于spring-boot-starter-parent -->
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.4.2.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>
    <!-- 創建項目是勾選的web依賴 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

    <!-- 每個項目都會自動添加一個test依賴 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
      <!-- Springboot的編譯插件 -->
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

這就是一個web項目的pom文件,可以看到只關聯了很少的依賴,這是因為我們繼承的spring-boot-starter-parent和關聯的spring-boot-starter-web本身已經為我們關聯了全部的依賴,如下是該項目所有的依賴包



運行Spring Boot項目

  1. maven運行:mvn spring-boot:run
  2. main函數運行:右鍵單擊SpringBootWebDemoApplication,選擇『Run 或者 Debug』;
  3. 推薦安裝JRebel插件,支持熱部署;
  4. 當然,也可以maven先打成jar,然后通過命令行執行java -jar xx.jar
  • 運行成功會看到控制臺打印了如下信息


  • 可以看到打印信息中有tomcat的啟動信息,說明springboot默認使用tomcat作為web運行容器,這點從上面的依賴包中也可以看到。因為當前項目并沒有開放任何服務,所以此時訪問8080端口會提示無服務


添加服務

  • 我們可以在項目中創建一個Controller控制器,比如DemoController
package com.example.Controller;

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

@RestController
public class DemoController {

    @RequestMapping("/")
    String index(){
        return "Hello Spring Boot!";
    }
}

一切似乎就是那么美好,我們什么都沒配置,一個web項目就這樣運行起來了,SpringBoot自動幫我們默認了一些常用的配置


自動配置原理說明

SpringBootWebDemoApplication類上的注解:@SpringBootApplication

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.autoconfigure.EnableAutoConfiguration;
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}
)}
)
public @interface SpringBootApplication {
    Class<?>[] exclude() default {};

    String[] excludeName() default {};

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

    @AliasFor(
        annotation = ComponentScan.class,
        attribute = "basePackageClasses"
    )
    Class<?>[] scanBasePackageClasses() default {};
}
  • @SpringBootConfiguration實際上就是@Configuration,說明這是一個JavaConfig
  • @ComponentScan,啟用注解自動掃描
  • @EnableAutoConfiguration的作用是根據類路徑中jar包是否存在來決定是否開啟某一個功能的自動配置,比如,我們項目中添加了spring-boot-starter-web依賴,因其關聯Tomcat和Srping MVC,所以類路徑下就會存在Tomcat和Spring MVC的jar包,SpringBoot項目掃描到這些jar包后會自動開啟兩者的配置,當然,這個配置是默認配置,我們可以根據需要進行修改(下文介紹)。
  • exclude和excludeName用于關閉指定的自動配置,比如關閉數據源相關的自動配置
@SpringBootApplication(exclude={DataSourceAutoConfiguration.class})
  • scanBasePackages和scanBasePackageClasses用于指定掃描的路徑,默認情況下會自動掃描被@SpringBootApplication注解的類(這里是SpringBootWebDemoApplication)的同級包以及子包中的Bean。比如我們創建的DemoController,因為開啟了SpringMVC自動配置,同時又在對應的路徑下,所以該Controller會被自動加載。比如我們這里指定掃描的包路徑如下:
@SpringBootApplication(scanBasePackages = {"com.temp.Controller"})

再次運行程序,發現原來的DemoController不能被訪問了,而『com.temp.Controller』下的controller卻可以被訪問。

那么問題來了,SpringBoot到底為我們自動配置了哪些功能呢?

  • 開啟Debug模式,方式有多種:
  • java -jar xx.jar --debug
  • 在IDE中執行Run時添加VM arguments:-Ddebug
  • 在項目resources下的application.properties文件中增加debug=true
  • Debug模式運行程序,打印信息中會顯示如下內容

啟動的自動配置



未啟用的自動配置


  • 從打印結果中看到,每一個*AutoConfiguration*都對應著一類功能的自動配置類,比如HttpEncodingAutoConfiguration:
HttpEncodingAutoConfiguration matched:
      - @ConditionalOnClass found required class 'org.springframework.web.filter.CharacterEncodingFilter' (OnClassCondition)
      - @ConditionalOnWebApplication (required) found StandardServletEnvironment (OnWebApplicationCondition)
      - @ConditionalOnProperty (spring.http.encoding.enabled) matched (OnPropertyCondition)
  • 開啟的自動配置中都會有@ConditionalOnClass@ConditionalOnWebApplication等標識,這是什么意思呢?為了弄清楚這個,我們需要先來認識一下@EnableAutoConfiguration

@EnableAutoConfiguration

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.autoconfigure.AutoConfigurationPackage;
import org.springframework.boot.autoconfigure.EnableAutoConfigurationImportSelector;
import org.springframework.context.annotation.Import;

@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@AutoConfigurationPackage
@Import({EnableAutoConfigurationImportSelector.class})
public @interface EnableAutoConfiguration {
    String ENABLED_OVERRIDE_PROPERTY = "spring.boot.enableautoconfiguration";

    Class<?>[] exclude() default {};

    String[] excludeName() default {};
}

  • 這里我們需要了解一下@Import注解中的EnableAutoConfigurationImportSelector

感興趣的可以看一下源碼,大體的功能就是掃描jar包里是否含有META-INF/spring.factories文件;
并在spring.factories中找到@EnableAutoConfiguration的全路徑名稱org.springframework.boot.autoconfigure.EnableAutoConfiguration這個key,該key對應的value就是用于聲明都需要啟用哪些自動配置類;
比如spring-boot-autoconfigure-1.4.2.RELEASE.jar中就有一個spring.factories,可以看到org.springframework.boot.autoconfigure.EnableAutoConfiguration參數中列出了自動配置類列表,而HttpEncodingAutoConfiguration這個自動配置類就是其聲明的;

HttpEncodingAutoConfiguration

  • 先看下源碼
@Configuration
@EnableConfigurationProperties({HttpEncodingProperties.class})
@ConditionalOnWebApplication
@ConditionalOnClass({CharacterEncodingFilter.class})
@ConditionalOnProperty(
    prefix = "spring.http.encoding",
    value = {"enabled"},
    matchIfMissing = true
)
public class HttpEncodingAutoConfiguration {
    private final HttpEncodingProperties properties;

    public HttpEncodingAutoConfiguration(HttpEncodingProperties properties) {
        this.properties = properties;
    }

    @Bean
    @ConditionalOnMissingBean({CharacterEncodingFilter.class})
    public CharacterEncodingFilter characterEncodingFilter() {
        OrderedCharacterEncodingFilter filter = new OrderedCharacterEncodingFilter();
        filter.setEncoding(this.properties.getCharset().name());
        filter.setForceRequestEncoding(this.properties.shouldForce(Type.REQUEST));
        filter.setForceResponseEncoding(this.properties.shouldForce(Type.RESPONSE));
        return filter;
    }

    //.......省略以下........
}
  • 熟悉JavaConfig的都會明白,這就是一個配置類@Configuration,并且通過@Bean注冊了一個CharacterEncodingFilter;

但是還有一些注解,是什么意思呢,我們分別說明:


  • @EnableConfigurationProperties:開啟屬性注入

本例中表示HttpEncodingProperties是屬性類,并使用@Autowired自動注入;
屬性類實際上是一個是注解了@ConfigurationProperties的JavaBean,SpringBoot將屬性文件(application.properties)中的鍵值對與JavaBean的屬性建立起一一對應關系:

@ConfigurationProperties(
    prefix = "spring.http.encoding" //屬性值的前綴
)

/*
舉例:application.properties中設置如下屬性
spring.http.encoding.charset=UTF-8
spring.http.encoding.force=true
*/
public class HttpEncodingProperties {
    private Charset charset;
    private Boolean force;
    //....屬性聲明及set、get方法........
    }

所有@ConditionalOn開頭的注解都是用于進行條件判斷的


  • @ConditionalOnWebApplication:當前項目是web項目的條件下才加載當前配置類
  • @ConditionalOnClass:當類路徑下有指定的類的條件下才加載當前配置類
//本例表示,當前類路徑(含jar)下必須存在CharacterEncodingFilter
@ConditionalOnClass({CharacterEncodingFilter.class})
  • @ConditionalOnProperty:當指定的屬性等于指定的值的情況下加載當前配置類
// spring.http.encoding=enabled
// matchIfMissing = true表示如果沒有在application.properties設置該屬性,則默認為條件符合
@ConditionalOnProperty(
    prefix = "spring.http.encoding",
    value = {"enabled"},
    matchIfMissing = true
)
  • @ConditionalOnMissingBean:當前容器里沒有指定的Bean的情況下
// 如果當前容器中找不到CharacterEncodingFilter實例,則創建當前的Bean
@ConditionalOnMissingBean({CharacterEncodingFilter.class})

通過上面的分析,應該可以明白SpringBoot是如何做到自動配置的,簡單總結如下:

  1. @SpringBootConfiguration實際上就是@Configuration,說明這是一個JavaConfig
  2. @EnableAutoConfiguration負責掃描jar包中的META-INF/spring.factories來找到要初始化的各種AutoConfiguration
  3. 各種@Conditional注解決定哪些Bean可以被容器初始化
  4. 如果希望進一步了解SpringBoot的自動配置,建議查看每一個AutoConfiguration類的源碼

除了上面介紹的,@Conditional注解還有如下形式

  • @ConditionalOnExpression:基于SpEL表達式作為條件判斷
  • @ConditionalOnJava:基于JAVA版本作為判斷條件
  • @ConditionalOnJndi:在JNDI存在的條件下查找指定的位置
  • @ConditionalOnMissingClass:當前類路徑下沒有指定的類的條件下
  • @ConditionalOnNotWebApplication:當前項目不是web項目的條件下
  • @ConditionalOnResource:類路徑下是否有指定的值
  • @ConditionalOnSingleCandidate:當指定的Bean在容器中只有一個的情況下

如果我們希望自己創建一個自動配置類(AutoConfiguration),則只需要在我們自己創建的JavaConfig中加上@ConditionalOn注解,并且在類路徑下創建META-INF/spring.factories,加入參數org.springframework.boot.autoconfigure.EnableAutoConfiguration=xxxxAutoConfiguration


SpringBoot的配置文件

  • SpringBoot支持常規的properties配置文件(application.properties),還支持yaml語言的配置文件(application.yml)
  • SpringBoot會從classpath下的/config目錄或者classpath的根目錄查找application.properties或application.yml
  • 如果要修改SpringBoot自動配置中默認配置,可以通過在配置文件中配置相應的參數即可
  • 比如,項目啟動時,tomcat默認的端口號是『8080』,訪問路徑是『/』,修改如下:
  • application.properties
server.port=8081
server.context-path=/demo
  • application.yml
server:
  port: 8081
  context-path: /demo
  • IntelliJ IDEA支持對properties和yml的代碼提示功能,編輯起來還是很方便的,不需要特別記住這些屬性名稱
  • SpringBoot默認使用priperites進行配置

SpringBoot的屬性可以通過多種方式指定,配置文件只是其中一種方式,常用的方式還有如下幾種,按加載的優先級列出:

命令行參數:java -jar xx.jar --server.port=8081 --server.context-path=/demo
操作系統環境變量:有些OS不支持使用.這種名字,如server.port,可以使用SERVER_PORT來配置。
項目中的配置文件:application.properties或者application.yml
項目依賴jar包中的配置文件:application.properties或者application.yml

關于SpringBoot支持的配置屬性可以查看官網地址1.4.2.RELEASE


Profile配置

  • 不同的環境可以使用不同的配置文件,application-{profile}.properties,比如

開發:application-rnd.properties
測試:application-release.properties
驗證:application-verify.properties
生產:application-prod.properties

  • 通過在application.properties(項目中必須包含該文件)中設置spring.profiles.active=prod來指定啟用哪一個Profile。

關于屬性配置還想多說的一些內容

  • application.properties也可以配置自定義屬性:my.name=hanqf
  • 通過@Value將屬性注入Bean屬性
@Value("${my.name}")
private String myName;
  • 通過@ConfigurationProperties將屬性注入Bean對象

使用prefix

my.name=hanqf
my.servers[0]=rnd.hanqf.com
my.servers[1]=release.hanqf.com
@ConfigurationProperties(prefix="my")
public class Config {
    private String name;
    private List<String> servers = new ArrayList<String>();//list需要初始化

    //....set and get method
}

不使用prefix

name=hanqf
jdbc.username=root
jdbc.password=root
@ConfigurationProperties
public class Config {
    private String name;
    private Jdbc jdbc;
    class Jdbc {
        private String username;
        private String password;
        //....set and get method
    }

    //....set and get method
}
  • 屬性占位符
app.name=MyApp
app.description=${app.name} is a Spring Boot application 

server.port=${port:8080} # 如果沒有設置port,則使用默認值8080
  • 屬性名匹配規則
@ConfigurationProperties(prefix="person")
public class Config {
    private String firstName;

    //....set and get method
}

firstName可以使用的屬性名如下:

person.firstName,標準的駝峰式命名
person.first-name,虛線(-)分割方式,推薦在.properties和.yml配置文件中使用
PERSON_FIRST_NAME,大寫下劃線形式,建議在系統環境變量中使用

日志配置

  • Spring Boot默認使用Logback作為日志框架,這是推薦的方式,如果希望修改為熟悉的log4j可以看下文

創建項目時我們引入了spring-boot-starter-web,其依賴spring-boot-starterspring-boot-starter又依賴于spring-boot-starter-logging,該依賴內容就是Spring Boot默認的日志框架Logback
Logback相關設置,可以在application.properties中進行如下配置:

# 日志文件路徑
logging.file=D:/my_log.log 

# 配置日志打印級別
logging.level.org.springframework=INFO

當然,也可以直接將自己的logback.xml放到項目根路徑下

  • 修改為log4j框架
    pom中排除對spring-boot-starter-logging的依賴,并加入對spring-boot-starter-log4j的依賴
    目前maven中央倉庫的最新版本是1.3.8.RELEASE
<dependency>  
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter</artifactId>
    <exclusions>
        <exclusion> 
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-logging</artifactId>
        </exclusion>
    </exclusions>
</dependency>

<dependency>  
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-log4j</artifactId>
    <version>1.3.8.RELEASE</version> 
</dependency>

項目根路徑下添加log4j.properties

  • 修改為log4j2框架
    與log4j類似,修改pom,增加spring-boot-starter-log4j2依賴
    目前maven中央倉庫的最新版本是1.4.2.RELEASE
<dependency>  
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter</artifactId>
    <exclusions>
        <exclusion> 
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-logging</artifactId>
        </exclusion>
    </exclusions>
</dependency>

<dependency>  
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-log4j2</artifactId>
    <version>1.4.2.RELEASE</version> 
</dependency>

項目根路徑下添加log4j2.xml


說明
這里需要說明一個問題,如果切換為其它log框架,debug=true將會失效,需要在各自的log配置文件中聲明,比如log4j需要添加log4j.logger.org.springframework.boot=debug


修改內置Tomcat為Jetty

  • 修改pom,去除spring-boot-starter-tomcat的依賴,增加spring-boot-starter-jetty依賴
    目前maven中央倉庫的最新版本是1.4.2.RELEASE
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
    <exclusions>
        <exclusion>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-tomcat</artifactId>
        </exclusion>
    </exclusions>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-jetty</artifactId>
    <version>1.4.2.RELEASE</version>
</dependency>
  • application.properties中的屬性配置與tomcat一致

修改內置Tomcat為Undertow容器

  • 修改pom,去除spring-boot-starter-tomcat的依賴,增加spring-boot-starter-undertow依賴
    目前maven中央倉庫的最新版本是1.4.2.RELEASE
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
    <exclusions>
        <exclusion>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-tomcat</artifactId>
        </exclusion>
    </exclusions>
</dependency>

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-undertow</artifactId>
    <version>1.4.2.RELEASE</version>
</dependency>
  • application.properties中的屬性配置與tomcat一致

單元測試

  • 創建一個單元測試的抽象父類,用于初始化必要的對象
package com.common;

import org.junit.Before;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.junit4.SpringRunner;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
import org.springframework.web.context.WebApplicationContext;

@RunWith(SpringRunner.class)
//1.4.2.RELEASE中不再需要@SpringApplicationConfiguration和@WebAppConfiguration
@SpringBootTest 
public abstract class SpringBootTestParent {

    public MockMvc mockMvc;

    @Autowired
    WebApplicationContext webApplicationContext;

    @Before
    public void setUp() throws Exception {
        mockMvc = MockMvcBuilders.webAppContextSetup(webApplicationContext).build();

    }
}
  • 繼承抽象父類,并實現測試邏輯
public class SpringBootWebDemoApplicationTests extends SpringBootTestParent{

    @Autowired
    DemoService demoService;

    @Test
    public void content(){
        String content = "456";
        System.out.println(demoService.printContent(content));
        Assert.assertEquals(content,demoService.printContent(content));
    }

    @Test
    public void  DemoControllerContent(){
        String uri = "/content/123";
        MvcResult mvcResult;
        try {
            mvcResult = mockMvc.perform(MockMvcRequestBuilders.get(uri)).andReturn();
            System.out.println(mvcResult.getResponse().getStatus() + "##" + mvcResult.getResponse().getContentAsString());
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

使用war包的形式運行項目

上面我們介紹了SpringBoot通過jar的形式運行項目的方法,這也是SpringBoot推薦的方式,因其內置Servlet容器,所以發布和部署都非常方便,但是某些情況下(比如使用JSP作為VIEW層,內置容器的形式并不能支持),我們希望將web項目部署到自己的容器中,這時候就需要將SpringBoot項目打成war包部署,有兩種方式:
1.創建項目時打包方式選擇:war


war項目目錄結構


2.將原打包方式為jar的項目修改為war形式
與war項目對比發現,通過修改如下內容,可以將jar項目修改為war項目
2.1 pom中將<packaging>jar</packaging>==><packaging>war</packaging>
2.2 pom中添加tomcat依賴,顯示聲明scope為provided,這樣打包時就不會將tomcat的jar包打到war中

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-tomcat</artifactId>
    <scope>provided</scope>
</dependency>

2.3 創建ServletInitializer

public class ServletInitializer extends SpringBootServletInitializer {
    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(DemoWarApplication.class);
    }
}

說明

  • Servlet3.0規范,支持將web.xml相關配置也硬編碼到代碼中,并由javax.servlet.ServletContainerInitializer的實現類負責在容器啟動時進行加載
  • spring提供了一個實現類org.springframework.web.SpringServletContainerInitializer,
    該類會調用所有org.springframework.web.WebApplicationInitializer的實現類的onStartup(ServletContext servletContext)方法,從而將相關的容器組件注冊到容器;
  • SpringBootServletInitializer就是WebApplicationInitializer的實現類;
  • 我之前寫過一篇SpringMVC4零配置的文章,對零配置感興趣的同學可以參考。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容