前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Springboot2

Springboot2

原创
作者头像
用户8126523
修改2023-04-25 23:35:57
4650
修改2023-04-25 23:35:57
举报
文章被收录于专栏:code1029

参考:https://www.yuque.com/leifengyang/springboot2

参考:https://www.bilibili.com/video/BV19K4y1L7MT?p=1&vd_source=0c3c1f43c75954a15fba4e42c1d7883e

1. HelloWorld

项目结构

1. pom.xml

代码语言:javascript
复制
<?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>springboot-test</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>pom</packaging>
    <modules>
        <module>springboot-01-hello</module>
    </modules>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.3.4.RELEASE</version>
    </parent>

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

    <properties>
        <maven.compiler.source>8</maven.compiler.source>
        <maven.compiler.target>8</maven.compiler.target>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    </properties>

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

</project>

2. MainApplication

代码语言:javascript
复制
package com.example;

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

/**
 * 主程序类
 * @SpringBootApplication:这是一个springboot应用
 */
@SpringBootApplication
public class MainApplication {
    public static void main(String[] args) {
        SpringApplication.run(MainApplication.class, args);
    }
}

3. HelloController

代码语言:javascript
复制
package com.example.controller;

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

@RestController
public class HelloController {
    @RequestMapping("/hello")
    public String home() {
        return "Hello world";
    }
}

4. 启动服务,浏览器访问

2. Springboot特点

2.1 依赖管理

2.1.1 父项目做依赖管理

代码语言:javascript
复制
<parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.3.4.RELEASE</version>
</parent>

点进spring-boot-starter-parent看到:
<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-dependencies</artifactId>
    <version>2.3.4.RELEASE</version>
</parent>

点进spring-boot-dependencies看到:
    几乎声明了所有开发中常用的依赖的版本号

2.1.2 开发导入starter场景启动器

代码语言:javascript
复制
<dependency>
     <groupId>org.springframework.boot</groupId>
     <artifactId>spring-boot-starter</artifactId>
     <version>2.3.4.RELEASE</version>
     <scope>compile</scope>
</dependency>

2.1.3 无需关注版本号,自动版本仲裁

  • spring-boot-dependencies几乎声明了所有开发中常用的依赖的版本号,引入依赖默认都可以不写版本=>自动版本仲裁

2.1.4 可以修改版本号

  • 引入非版本仲裁的jar,要写版本号
  • 查看spring-boot-dependencies里面规定当前依赖的版本用的 key,版本不一致=>在当前项目里面重写配置
代码语言:javascript
复制
<properties>
    <mysql.version>5.1.43</mysql.version>
</properties>

2.2 自动配置

2.2.1 自动配好Tomcat

  • 引入Tomcat依赖
代码语言:javascript
复制
<dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-tomcat</artifactId>
      <version>2.3.4.RELEASE</version>
      <scope>compile</scope>
</dependency>
  • 配置Tomcat ???

2.2.2 自动配好SpringMVC

  • 引入SpringMVC全套组件:spring-boot-starter-web引入
  • 自动配好SpringMVC常用组件(功能)

2.2.3 自动配好Web常见功能

SpringBoot帮我们配置好了所有web开发的常见场景

  • dispatcherServlet
  • 字符编码:characterEncodingFilter
  • 文件上传:multipartResolver

2.2.4 默认的包结构

  • 主程序所在包及其下面的所有子包里面的组件都会被默认扫描进来
  • 无需以前的包扫描配置
  • 想要改变扫描路径,@SpringBootApplication(scanBasePackages="com.example")
    • 或者@ComponentScan 指定扫描路径
代码语言:javascript
复制
@SpringBootApplication
等同于
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan("com.example")

2.2.5 各种配置拥有默认值

  • application.properties:默认配置最终都是映射到某个类上,如:MultipartProperties
  • application.properties配置文件的值最终会绑定每个类上,这个类会在容器中创建对象

2.2.6 按需加载所有自动配置项

  • 非常多的starter
  • 引入了哪些场景这个场景的自动配置才会开启
  • SpringBoot所有的自动配置功能都在 spring-boot-autoconfigure 包里面
代码语言:javascript
复制
package com.example;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.ComponentScan;

/**
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan("com.example")
等价于@SpringBootApplication(scanBasePackages="com.example")
 默认扫描主程序所在的包
*/
@SpringBootApplication
public class MainApplication {
    public static void main(String[] args) {
        //1、返回我们IOC容器
        ConfigurableApplicationContext run = SpringApplication.run(MainApplication.class, args);

        //2、查看容器里面的组件
        String[] names = run.getBeanDefinitionNames();
        for (String name : names) {
            System.out.println("组件:" + name);
        }
    }
}

3. 自动配置注解

3.1 @Configuration

  • Full模式与Lite模式
  • 项目结构
  • User
代码语言:javascript
复制
package com.example.bean;

public class User {
    private String name;
    private int age;

    private Pet pet;

    public User() {
    }

    public User(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public Pet getPet() {
        return pet;
    }

    public void setPet(Pet pet) {
        this.pet = pet;
    }

    @Override
    public String toString() {
        return "User{" +
                "name='" + name + '\'' +
                ", age=" + age +
                ", pet=" + pet +
                '}';
    }
}
  • Pet
代码语言:javascript
复制
package com.example.bean;

public class Pet {
    private String name;

    public Pet() {
    }

    public Pet(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Pet{" +
                "name='" + name + '\'' +
                '}';
    }
}
  • MainConfig
代码语言:javascript
复制
package com.example.config;

import com.example.bean.Pet;
import com.example.bean.User;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration(proxyBeanMethods=true) // 告诉springboot这是一个配置类
public class MainConfig {
    @Bean
    public User userBean(){
        User u = new User("zhangsan", 18);
        u.setPet(petBean());
        return u;
    }

    @Bean
    public Pet petBean(){
        Pet p = new Pet("cat");
        return p;
    }
}
  • MainApplication
代码语言:javascript
复制
package com.example;

import com.example.bean.Pet;
import com.example.bean.User;
import com.example.config.MainConfig;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.ComponentScan;

/**
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan("com.example")
等价于@SpringBootApplication(scanBasePackages="com.example")
 默认扫描主程序所在的包
*/
@SpringBootApplication
public class MainApplication {
    public static void main(String[] args) {
        //1、返回我们IOC容器
        ConfigurableApplicationContext run = SpringApplication.run(MainApplication.class, args);

        //2、查看容器里面的组件
        String[] names = run.getBeanDefinitionNames();
        for (String name : names) {
            System.out.println("组件:" + name);
        }

        // 3. 从容器中获取组件
        User user = (User) run.getBean("userBean");
        User user2 = (User) run.getBean("userBean");
        System.out.println("组件默认是单例的:" + (user==user2));

        // 4. 配置类也是组件
        MainConfig bean = run.getBean(MainConfig.class);
        System.out.println("配置类本身也是组件:" + bean);

        // 5. proxyBeanMethods = true, mainConfig就是被增强的代理对象
        // springboot总会检查组件是否在容器中存在
        // 保持组件单实例
        // 外部无论对配置类中的这个组件注册方法调用多少次,获取的都是之前注册容器中的单实例对象
        User user3 = bean.userBean();
        User user4 = bean.userBean();
        System.out.println("主配置是否为代理对象: "+(user3==user4));

        // full: proxyBeanMethods=true  => 应用场景: 解决组件依赖
        // lite: proxyBeanMethods=false => 配置类在容器中不会保存代理对象,在外边调用方法,每次都会产生一个新对象

        // Full: 保证每个@Bean方法被调用多少次返回的组件都是单实例的。类组件之间有依赖关系,方法会被调用得到之前单实例组件,用Full模式
        // Lite: 每个@Bean方法被调用多少次返回的组件都是新创建的。类组件之间无依赖关系用Lite模式加速容器启动过程,减少判断
        // 组件依赖必须使用Full模式默认。其他默认是否Lite模式
        Pet pet = (Pet) run.getBean("petBean");
        System.out.println("proxyBeanMethods组件依赖" + (user.getPet()==pet));
    }
}

3.2 @Bean、@Component、@Controller、@Service、@Repository

  • 项目结构
  • MainConfig
代码语言:javascript
复制
package com.example.config;

import com.example.bean.Pet;
import com.example.bean.User;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class MainConfig {
}
  • User
代码语言:javascript
复制
package com.example.bean;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;

@Component("userBean")
public class User {
    private String name;
    private int age;

    @Autowired
    private Pet pet;

    public User() {
    }

    public User(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public Pet getPet() {
        return pet;
    }

    public void setPet(Pet pet) {
        this.pet = pet;
    }

    @Override
    public String toString() {
        return "User{" +
                "name='" + name + '\'' +
                ", age=" + age +
                ", pet=" + pet +
                '}';
    }
}
  • Pet
代码语言:javascript
复制
package com.example.bean;

import org.springframework.stereotype.Component;

@Component("petBean")
public class Pet {
    private String name;

    public Pet() {
    }

    public Pet(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Pet{" +
                "name='" + name + '\'' +
                '}';
    }
}
  • MainApplication
代码语言:javascript
复制
package com.example;

import com.example.bean.Pet;
import com.example.bean.User;
import com.example.config.MainConfig;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.ComponentScan;

/**
 * @SpringBootConfiguration
 * @EnableAutoConfiguration
 * @ComponentScan("com.example") 等价于@SpringBootApplication(scanBasePackages="com.example")
 * 默认扫描主程序所在的包
 */
@SpringBootApplication
public class MainApplication {
    public static void main(String[] args) {
        //1、返回我们IOC容器
        ConfigurableApplicationContext run = SpringApplication.run(MainApplication.class, args);

        //2、查看容器里面的组件
        String[] names = run.getBeanDefinitionNames();
        for (String name : names) {
            System.out.println("组件:" + name);
        }

        // 3. 从容器中获取组件
        User user = (User) run.getBean("userBean");
        User user2 = (User) run.getBean("userBean");
        System.out.println("组件默认是单例的:" + (user == user2));

        // 4. 配置类也是组件
        MainConfig bean = run.getBean(MainConfig.class);
        System.out.println("配置类本身也是组件:" + bean);

        // 5. 组件依赖
        Pet pet = (Pet) run.getBean("petBean");
        System.out.println("组件依赖" + (user.getPet() == pet));
    }
}

3.3 @Import、@Conditional、@ImportResource、@ConfigurationProperties

@Import:给容器中自动创建出指定类型的组件、默认组件的名字就是全类名

@Conditional:条件装配,满足Conditional指定的条件,则进行组件注入

@ImportResource:原生配置文件引入

@ConfigurationProperties:配置文件中的配置项绑定给组件的属性

  • 项目结构
  • MainApplication
代码语言:javascript
复制
package com.example;

import ch.qos.logback.core.db.DBHelper;
import com.example.bean.Pet;
import com.example.bean.User;
import com.example.config.MainConfig;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.SpringBootConfiguration;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.ComponentScan;

import java.util.Arrays;

/**
 @SpringBootConfiguration
 @EnableAutoConfiguration
 @ComponentScan("com.example")
 等价于@SpringBootApplication(scanBasePackages="com.example")
 默认扫描主程序所在的包
 */


/**
 * @Import:给容器中自动创建出指定类型的组件、默认组件的名字就是全类名
 * @Conditional:条件装配,满足Conditional指定的条件,则进行组件注入
 * @ImportResource:原生配置文件引入
 * @ConfigurationProperties:配置文件中的配置项绑定给组件的属性
 */
@SpringBootApplication
public class MainApplication {
    public static void main(String[] args) {
        //1、返回我们IOC容器
        ConfigurableApplicationContext run = SpringApplication.run(MainApplication.class, args);

        //2、查看容器里面的组件
        String[] names = run.getBeanDefinitionNames();
        for (String name : names) {
            System.out.println("组件:" + name);
        }

        // 3. 获取组件
        Boolean flag = run.containsBean("petBean");
        System.out.println("容器中是否存在petBean组件:" + flag);

        Boolean flag2 = run.containsBean("userBean");
        System.out.println("容器中是否存在userBean组件:" + flag2);
        
        // 4. 容器中组件数量
        System.out.println("组件数量:" + run.getBeanDefinitionCount()); // 167
    }
}
  • mainApplication.xml
代码语言:javascript
复制
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns="http://www.springframework.org/schema/beans"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <bean id="petBeanXml" class="com.example.bean.Pet">
        <property name="name" value="cat"></property>
    </bean>

    <bean id="userBeanXml" class="com.example.bean.User">
        <property name="pet" ref="petBeanXml"></property>
        <property name="name" value="zhangsan"></property>
        <property name="age" value="18"></property>
    </bean>
</beans>
  • User
代码语言:javascript
复制
package com.example.bean;

public class User {
    private String name;
    private int age;

    private Pet pet;

    public User() {
    }

    public User(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public Pet getPet() {
        return pet;
    }

    public void setPet(Pet pet) {
        this.pet = pet;
    }

    @Override
    public String toString() {
        return "User{" +
                "name='" + name + '\'' +
                ", age=" + age +
                ", pet=" + pet +
                '}';
    }
}
  • Pet
代码语言:javascript
复制
package com.example.bean;

public class Pet {
    private String name;

    public Pet() {
    }

    public Pet(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Pet{" +
                "name='" + name + '\'' +
                '}';
    }
}
  • Car
代码语言:javascript
复制
package com.example.bean;

import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;

// @Component 
// MainConfig中使用了@EnableConfigurationProperties(Car.class),则不用@Component
@ConfigurationProperties(prefix = "car")
public class Car {
    private String brand;
    private double price;

    public Car() {
    }

    public Car(String brand, double price) {
        this.brand = brand;
        this.price = price;
    }

    public String getBrand() {
        return brand;
    }

    public void setBrand(String brand) {
        this.brand = brand;
    }

    public double getPrice() {
        return price;
    }

    public void setPrice(double price) {
        this.price = price;
    }

    @Override
    public String toString() {
        return "Car{" +
                "brand='" + brand + '\'' +
                ", price=" + price +
                '}';
    }
}
  • MainConfig
代码语言:javascript
复制
package com.example.config;

import ch.qos.logback.core.db.DBHelper;
import com.example.bean.Car;
import com.example.bean.Pet;
import com.example.bean.User;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.*;

// @ConditionalOnBean(name="petBean") // 有petBean类里的组件注册才生效,否则都不生效
@EnableConfigurationProperties(Car.class)
// @EnableConfigurationProperties(Car.class)的作用:
// 1. 开启Car配置绑定功能
// 2. 把这个Car这个组件自动注册到容器中
@ImportResource("classpath:mainApplication.xml")
@Import({User.class, DBHelper.class})
@Configuration(proxyBeanMethods=true) // 告诉springboot这是一个配置类
public class MainConfig {
    @ConditionalOnBean(name="petBean") // 容器中存在petBean才执行userBean的组件注册
    @Bean
    public User userBean(){
        User u = new User("zhangsan", 18);
        u.setPet(petBean());
        return u;
    }

    // @Bean
    public Pet petBean(){
        Pet p = new Pet("cat");
        return p;
    }
}

4. 自动配置原理

4.1 引导加载自动配置类

  • @SpringBootApplication主要组成:@SpringBootConfiguration、@EnableAutoConfiguration、@ComponentScan
代码语言:javascript
复制
@SpringBootConfiguration
@EnableAutoConfiguration
@ComponentScan(
    excludeFilters = {@Filter(
    type = FilterType.CUSTOM,
    classes = {TypeExcludeFilter.class}
), @Filter(
    type = FilterType.CUSTOM,
    classes = {AutoConfigurationExcludeFilter.class}
)}
)
public @interface SpringBootApplication {}

4.1.1 @SpringBootConfiguration

代码语言:javascript
复制
@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Configuration 
// SpringBootConfiguration用来注解 配置类 => MainApplication是一个配置类(核心配置类)
public @interface SpringBootConfiguration {
    @AliasFor(
        annotation = Configuration.class
    )
    boolean proxyBeanMethods() default true;
}

4.1.2 @ComponentScan:包扫描,指定要扫描哪些

  • 两个自定义扫描器

4.1.3 @EnableAutoConfiguration

代码语言:javascript
复制
@AutoConfigurationPackage
@Import({AutoConfigurationImportSelector.class})
public @interface EnableAutoConfiguration {}
  • @AutoConfigurationPackage
代码语言:javascript
复制
@Import({AutoConfigurationPackages.Registrar.class}) 
// 给容器中导入一个组件
// 指定了默认的包规则
public @interface AutoConfigurationPackage {}

// 利用Registrar给容器中导入一系列组件
// 将指定的MainApplication所在包下的所有组件导入进来
  • @Import({AutoConfigurationImportSelector.class})
代码语言:javascript
复制
1. 利用getAutoConfigurationEntry(annotationMetadata)给容器中批量导入一些组件
2. 调用List<String> configurations = getCandidateConfigurations(annotationMetadata, attributes)获取到所有需要导入到容器中的配置类
3. 利用工厂加载 Map<String, List<String>> loadSpringFactories(@Nullable ClassLoader classLoader)得到所有的组件
4. 从META-INF/spring.factories位置来加载一个文件。
    默认扫描我们当前系统里面所有META-INF/spring.factories位置的文件
    spring-boot-autoconfigure-2.3.4.RELEASE.jar包里面也有META-INF/spring.factories
    文件里面写死了spring-boot一启动就要给容器中加载的所有配置类

4.2 按需开启自动配置项

  • spring.factories
  • @Conditional
代码语言:javascript
复制
1. 虽然我们127个场景的所有自动配置启动的时候默认全部加载。
    META-INF/spring.factories文件中:xxxxAutoConfiguration
2. 按照条件装配规则(@Conditional),最终会按需配置。
    eg. @ConditionalOnClass({Gson.class})

4.3 修改默认配置

代码语言:javascript
复制
@Bean
@ConditionalOnBean(MultipartResolver.class)  //容器中有这个类型组件
@ConditionalOnMissingBean(name = DispatcherServlet.MULTIPART_RESOLVER_BEAN_NAME) //容器中没有这个名字 multipartResolver 的组件
public MultipartResolver multipartResolver(MultipartResolver resolver) {
    //给@Bean标注的方法传入了对象参数,这个参数的值就会从容器中找。
    //SpringMVC multipartResolver。防止有些用户配置的文件上传解析器不符合规范
	// Detect if the user has created a MultipartResolver but named it incorrectly
	return resolver;
}

SpringBoot默认会在底层配好所有的组件。但是如果用户自己配置了以用户的优先

代码语言:javascript
复制
@Bean
@ConditionalOnMissingBean
public CharacterEncodingFilter characterEncodingFilter() {}

总结:

  • SpringBoot先加载所有的自动配置类 xxxxxAutoConfiguration
  • 每个自动配置类按照条件进行生效,默认都会绑定配置文件指定的值。xxxxProperties里面拿。xxxProperties和配置文件进行了绑定
  • 生效的配置类就会给容器中装配很多组件(pom.xml配置了)
  • 只要容器中有这些组件,相当于这些功能就有了
  • 定制化配置
    • 用户直接自己@Bean替换底层的组件
    • 用户去看这个组件是获取的配置文件什么值就去修改

xxxxxAutoConfiguration ---> 组件 ---> xxxxProperties里面拿值 ----> application.properties

4,4 最佳实践

代码语言:javascript
复制
spring.banner.image.location=classpath:timg.jpg

4.5 简化开发

4.5.1 lombok

  • 引入依赖
代码语言:javascript
复制
<dependency>
    <groupId>org.projectlombok</groupId>
    <artifactId>lombok</artifactId>
</dependency>
  • idea安装插件
  • 使用
代码语言:javascript
复制
@ToString // toString
@Data // getter、setter
@AllArgsConstructor // 全参构造器
@NoArgsConstructor // 无参构造器
@Slf4j // 日志
  • 例子
代码语言:javascript
复制
package com.example.bean;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.ToString;

@ToString // toString
@Data // getter、setter
@AllArgsConstructor // 全参构造器
@NoArgsConstructor // 无参构造器
public class LombokBean {
    private String str;
    private int i;
}

代码语言:javascript
复制
import com.example.bean.LombokBean;
import lombok.extern.slf4j.Slf4j;
import org.junit.Test;

@Slf4j
public class LombokBeanTest {
    @Test
    public void testLombokBean(){
        LombokBean o = new LombokBean();
        o.setStr("abc");
        o.setI(10);
        System.out.println(o);
        log.info(o.toString());
    }
}

4.5.2 dev-tools

代码语言:javascript
复制
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-devtools</artifactId>
    <optional>true</optional>
</dependency>
  • CTRL+F9: 自动重启
  • SHIFT+F10: 重启
  • JREBEL:IDEA 安装插件 热更新

4.5.3 Spring Initailizr(项目初始化向导)

  • 新建项目
  • 下一步(aliyun仓库没有这个版本的spring-boot-starter-parent,换成了2.7.8版本)
  • 新窗口打开项目,项目结构,可以删除不相关的文件&文件夹
  • 配置maven
  • 重新加载项目
  • 引入依赖
代码语言:javascript
复制
<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>5.1.47</version>
</dependency>
  • 添加配置
代码语言:javascript
复制
server.port=9999

spring.datasource.driver-class-name=com.mysql.jdbc.Driver
spring.datasource.url=jdbc:mysql://127.0.0.1:3306/test?useSSL=false&useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai
spring.datasource.username=root
spring.datasource.password=123456

spring.redis.host=localhost
spring.redis.port=6379
spring.redis.password=redis
spring.redis.database=0
  • 测试项目

5. 配置文件

5.1 SpringBoot2核心技术-核心功能

5.2 文件类型

5.2.1 properties

  • 同以前的properties用法

5.2.2 yaml

  • YAML 是 "YAML Ain't Markup Language"(YAML 不是一种标记语言)的递归缩写。在开发的这种语言时,YAML 的意思其实是:"Yet Another Markup Language"(仍是一种标记语言)。 非常适合用来做以数据为中心的配置文件
  • 基本语法
    • key: value;kv之间有空格
    • 大小写敏感
    • 使用缩进表示层级关系
    • 缩进不允许使用tab,只允许空格
    • 缩进的空格数不重要,只要相同层级的元素左对齐即可
    • #表示注释
    • 字符串无需加引号,如果要加,单引号('')与双引号("")表示字符串内容=>会被 转义/不转义

5.2.3 数据类型

  • 字面量:单个的、不可再分的值。date、boolean、string、number、null
代码语言:javascript
复制
k: v
  • 对象:键值对的集合。map、hash、set、object
代码语言:javascript
复制
行内写法:  k: {k1:v1,k2:v2,k3:v3}
#或
k: 
  k1: v1
  k2: v2
  k3: v3
  • 数组:一组按次序排列的值。array、list、queue
代码语言:javascript
复制
行内写法:  k: [v1,v2,v3]
#或者
k:
 - v1
 - v2
 - v3

5.3 配置提示

  • 自定义的类和配置文件绑定一般没有提示
代码语言:javascript
复制
<!-- 配置提示 -->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-configuration-processor</artifactId>
    <optional>true</optional>
</dependency>

<build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <configuration>
                    <excludes>
                        <exclude>
                            <groupId>org.springframework.boot</groupId>
                            <artifactId>spring-boot-configuration-processor</artifactId>
                        </exclude>
                    </excludes>
                </configuration>
            </plugin>
        </plugins>
    </build>

5.4 例子

  • 新建模块
  • MainApplication
代码语言:javascript
复制
package com.example;

import com.example.bean.Person;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.context.properties.EnableConfigurationProperties;


/**
 * yaml
 */


@SpringBootApplication
@EnableConfigurationProperties(Person.class)
public class MainApplication {
    public static void main(String[] args) {
        SpringApplication.run(MainApplication.class, args);

    }
}
  • Person
代码语言:javascript
复制
package com.example.bean;

import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;

import java.util.List;
import java.util.Set;
import java.util.Date;
import java.util.Map;

@Data
@Component
@ConfigurationProperties(prefix = "person")
public class Person {

    private String userName;
    private Boolean boss;
    private Date birth;
    private Integer age;
    private Pet pet;
    private String[] interests;
    private List<String> animal;
    private Map<String, Object> score;
    private Set<Double> salarys;
    private Map<String, List<Pet>> allPets;
}
  • Pet
代码语言:javascript
复制
package com.example.bean;


import lombok.Data;

@Data
public class Pet {
    private String name;
    private Double weight;
}
  • PersonController
代码语言:javascript
复制
package com.example.controller;

import com.example.bean.Person;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class PersonController {
    @Autowired
    Person person;

    @RequestMapping("person")
    public String getPerson(){
        return person.toString();
    }
}
  • application.properties
代码语言:javascript
复制
server.port=9991
  • application.yml
    • application.properties和application.yml配置了相同项,以application.properties配的为准
代码语言:javascript
复制
server:
  port: 9999

# yaml表示以上对象
person:
  userName: zhangsan
  boss: false
  birth: 2019/12/12 20:12:33
  age: 18
  pet:
    name: tomcat
    weight: 23.4
  interests: [篮球,游泳]
  animal:
    - jerry
    - mario
  score:
    english:
      first: 30
      second: 40
      third: 50
    math: [131,140,148]  # { 0 = 131, 1 = 140, 2 = 148 }
    chinese: {first: 128,second: 136}
  salarys: [3999,4999.98,5999.99]
  allPets:
    sick:
      - {name: tom,weight: 10.1}
      - {name: jerry,weight: 47.0}
    health: [{name: mario,weight: 47.1}]

6. Web开发

6.1 静态资源访问

6.1.1 静态资源目录

  • 只要静态资源放在类路径下:/static (or /public or /resources or /META-INF/resources
  • 访问 : 当前项目根路径/ + 静态资源名
  • 原理: 静态映射 /**。
  • 请求进来,先去找Controller看能不能处理。不能处理的所有请求又都交给静态资源处理器。静态资源也找不到则响应404页面

6.1.2 静态资源访问前缀

  • 默认无前缀
  • 改变默认的静态资源路径
代码语言:javascript
复制
spring:
  mvc:
    static-path-pattern: /res/**
  • 当前项目 + static-path-pattern + 静态资源名 = 静态资源文件夹下找

6.1.3 静态资源保存目录

代码语言:javascript
复制
spring:
  resources:
    static-locations: [classpath:/haha/]

6.1.4 webjar

代码语言:javascript
复制
<dependency>
    <groupId>org.webjars</groupId>
    <artifactId>jquery</artifactId>
    <version>3.5.1</version>
</dependency>

6.2 欢迎页

  • 静态资源路径下 index.html
    • 可以配置静态资源路径
    • 但是不可以配置静态资源的访问前缀。否则导致 index.html不能被默认访问
代码语言:javascript
复制
spring:
#  mvc:
#    static-path-pattern: /res/**   这个会导致welcome page功能失效

  resources:
    static-locations: [classpath:/haha/]
  • controller能处理/index
  • 操作
    • 静态资源路径下,新增index.html文件
    • 启动服务,静态资源路径访问前缀/index.html,可以访问index.html文件
    • 直接访问根路径,404
    • 注释配置静态资源的访问前缀
    • 重启服务,访问根路径

6.3 自定义 Favicon

  • favicon.ico 放在静态资源目录下即可
代码语言:javascript
复制
spring:
#  mvc:
#    static-path-pattern: /res/**   这个会导致 Favicon 功能失效

重启服务,浏览器

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 1. HelloWorld
  • 2. Springboot特点
    • 2.1 依赖管理
      • 2.1.1 父项目做依赖管理
      • 2.1.2 开发导入starter场景启动器
      • 2.1.3 无需关注版本号,自动版本仲裁
      • 2.1.4 可以修改版本号
    • 2.2 自动配置
      • 2.2.1 自动配好Tomcat
      • 2.2.2 自动配好SpringMVC
      • 2.2.3 自动配好Web常见功能
      • 2.2.4 默认的包结构
      • 2.2.5 各种配置拥有默认值
      • 2.2.6 按需加载所有自动配置项
  • 3. 自动配置注解
    • 3.1 @Configuration
      • 3.2 @Bean、@Component、@Controller、@Service、@Repository
        • 3.3 @Import、@Conditional、@ImportResource、@ConfigurationProperties
        • 4. 自动配置原理
          • 4.1 引导加载自动配置类
            • 4.1.1 @SpringBootConfiguration
            • 4.1.2 @ComponentScan:包扫描,指定要扫描哪些
            • 4.1.3 @EnableAutoConfiguration
          • 4.2 按需开启自动配置项
            • 4.3 修改默认配置
              • 4,4 最佳实践
                • 4.5 简化开发
                  • 4.5.1 lombok
                  • 4.5.2 dev-tools
                  • 4.5.3 Spring Initailizr(项目初始化向导)
              • 5. 配置文件
                • 5.1 SpringBoot2核心技术-核心功能
                  • 5.2 文件类型
                    • 5.2.1 properties
                    • 5.2.2 yaml
                    • 5.2.3 数据类型
                  • 5.3 配置提示
                    • 5.4 例子
                    • 6. Web开发
                      • 6.1 静态资源访问
                        • 6.1.1 静态资源目录
                        • 6.1.2 静态资源访问前缀
                        • 6.1.3 静态资源保存目录
                        • 6.1.4 webjar
                      • 6.2 欢迎页
                        • 6.3 自定义 Favicon
                        相关产品与服务
                        容器服务
                        腾讯云容器服务(Tencent Kubernetes Engine, TKE)基于原生 kubernetes 提供以容器为核心的、高度可扩展的高性能容器管理服务,覆盖 Serverless、边缘计算、分布式云等多种业务部署场景,业内首创单个集群兼容多种计算节点的容器资源管理模式。同时产品作为云原生 Finops 领先布道者,主导开源项目Crane,全面助力客户实现资源优化、成本控制。
                        领券
                        问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档