25.1 Spring Boot基础



一、主要内容

介绍Spring Boot的特点、配置、小案例等,旨在夯实基础。

二、Spring Boot基础

2.1 本课介绍

1.Spring Boot核心特点

Spring Boot,与之前讲过的Spring什么关系?与之前项目使用的SSM框架,是什么关系?它很出名,有什么核心特点和好处呢?

2.Spring Boot版本介绍

3.新建演示第一个Spring Boot项目(官网、IDEA两种方式)

4.小案例:查询同学信息

入门合适:开发接口、打通服务层、调动数据库查询出数据,跑通整个流程。

从0到1。

三、Spring Boot核心特点

3.1 Spring Boot简介

3.2 核心特点:6个

其中:

  • 3的意思:

    以前:将Tomcat作为容器,将项目打成war包放入Tomcat中,来运行应用。

    现在:Spring Boot框架内部就已嵌入了Tomcat,不需要额外的启动程序、环境配置,只需要把当前项目看作一个Java程序运行,就能启动起来。即运行部署很方便。

关于jar包、war包的打包对比:

jar包、war包都是压缩文件

对比Jar包War包
名称Java Archive
Java归档文件
Web Archive
可以直接运行的Web模块和项目
本质别人写好的一些类,对这些类进行打包,可以引到自己的项目中去。一般放在lib目录下因为是web应用程序的格式,会按一定目录结构来组织,包括WEB-INF目录、web.xml、classes目录等

3.3 前生后世

Spring、Spring Boot、Spring Cloud的关系:

3.3 版本

1.官网

2.版本是否追新,最新的=最好?

不是。因为:

  • 虽然Spring Boot版本提高了,但是很多其他配套的组件需要适配的过程。

​ 比如:MyBatis、Redis要去适应Spring Boot,是需要时间的,不一定能提供良好的支持。

  • 稳定性。最新版的稳定性一般不好,而且所谓的新功能不一定能用到

3.Spring Boot 2.0 更新点

以下是版本升级的迁移指导:

4.是否要升级新版本?

  • 新项目:直接选2.0以后的版本
  • 旧项目:一般不升级

    如果在需求上、功能上,能够满足你现有的业务,没必要升级。因为就算升级,很多的代码、功能就不兼容了,而且很难去改正它,很多坑。

四、开发第一个Spring Boot程序

4.1 新建项目的两种方式

1.Spring官网的方式

  • 上面Spring Boot版本选择项很少,可以先勾选,后续在配置文件中进行更改即可
  • 上面就反映了Spring Boot的第二个特点:起步依赖,starter一站式

这样就会自动生成一个配置好的项目包:

2.IDEA集成的方式

更简便

initialize

at the beginning,初始化

跳转到如下界面:

选择依赖:

下面就反映了Spring Boot的第二个特点:起步依赖,starter一站式

  • 上面Spring Boot的版本会在后续pom.xml文件中进行更改,因为本项目使用的版本是2.2.1.RELEASE

填写项目名称:

自动生成了如下的项目:

这样就会自动生成一个已配置好的项目:

4.2 项目的结构分析

1.

在工程的配置文件pom.xml中:

  • 第一次创建Spring Boot项目,依赖会自动下载可能会持续10分钟左右(六十个依赖左右)
  • 再有三处更改,如下:
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
               // 部分1
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.2.1.RELEASE</version>                        <!--1.这里更改版本-->
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    
    <groupId>com.imooc</groupId>
    <artifactId>spring-boot-learn</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>spring-boot-learn</name>
    <description>Demo project for Spring Boot</description>

    <properties>
        <java.version>17</java.version>
    </properties>
    <!--2.阿里云Maven镜像-->
    <repositories>
        <repository>
            <id>aliyun</id>
            <name>aliyun</name>
            <url>https://maven.aliyun.com/repository/public</url>
        </repository>
    </repositories>
    <pluginRepositories>
        <pluginRepository>
            <id>aliyun</id>
            <name>aliyun</name>
            <url>https://maven.aliyun.com/repository/public</url>
        </pluginRepository>
    </pluginRepositories>
                // 部分2
    <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>
                // 部分3
    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>2.2.1.RELEASE</version>                <!--3.这里加上版本信息,否则会出错-->
            </plugin>
        </plugins>
    </build>

</project>

上述工程的配置文件pom.xml的结构为:

都是自动生成

2.

项目的结构共三部分:

见下:

其中 :

  • 测试类不需要额外关心,主要关心主启动类、配置文件,因为后续会使用到

4. 3 完成第一个接口

1.Web项目的三层结构

2.开发第一个接口(controller层的类)

新建包controller,新建类ParaController

/**
 * 演示接口和传参
 */
@RestController                                 // @Controller  + 返回的是json格式的,而不是一个页面
public class ParaController {

    @GetMapping("/firstrequest")
    public String firstRequest(){
        return "Hello Spring Boot,我的第一个Spring Boot接口";
    }

}

在自定义生成的启动类中,进行启动:

启动成功:

浏览器:

成功得到返回值

以上,一个基础的接口,就完成了。

五、SpringBoot配置详解

5.1 接收请求参数

不足:

以上的接口内容是写死的,没有办法对参数进行接收和处理。

解决如下。

1.Get请求:用注解@RequestParam

当发送Get请求,用问号?传参时:

那么,可以用注解@RequestParam,拿到请求中的参数,然后赋值给方法参数

在controller控制层的ParaController类中:

/**
 * 演示接口和传参
 */
@RestController                                 // @Controller  + 返回是json格式的,而不是一个页面
public class ParaController {


    @GetMapping("/firstrequest")
    public String firstRequest(){
        return "Hello Spring Boot,我的第一个Spring Boot接口";
    }


    @GetMapping("/para")
    public String requestPara(@RequestParam Integer num) {      // @RequestParam:“我能从请求中拿到参数,然后赋值给方法!”
        num = num + 1;
        return "我收到了参数:" + num;
    }


}

浏览器:

成功显示,说明成功的拿到了请求中的参数

2.Post请求:用注解@RequestBody

当接收Post请求时,通常会封装成一个实体类,来统一的处理和映射。

实体类Student

/**
 * 学生实体类
 */
public class Student {

    private Integer id;
    private String name;

    public Student() {
    }

    public Student(Integer id, String name) {       // 全参的构造方法
        this.id = id;
        this.name = name;
    }

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

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

    @Override
    public String toString() {
        return "Student{" +
                "id=" + id +
                ", name='" + name + '\'' +
                '}';
    }
}

在controller控制层的ParaController类中:

用注解@RequestBody,拿到post请求中的参数,然后自动赋值和一一映射给实体类:

/**
 * 演示接口和传参
 */
@RestController                                 // @Controller  + 返回是json格式的,而不是一个页面
public class ParaController {


    @GetMapping("/firstrequest")
    public String firstRequest(){
        return "Hello Spring Boot,我的第一个Spring Boot接口";
    }


    @GetMapping("/para")
    public String requestPara(@RequestParam Integer num) {      // @RequestParam:“我能从请求中拿到参数!”
        num = num + 1;
        return "我收到了参数:" + num;
    }


    @PostMapping("/post")
    public String postRequest(@RequestBody Student student) {      // @RequestBody:“我能从post请求中拿到参数!”
        return "我收到了post参数:" + student;
    }


}

提交post请求,是很难在浏览器中进行模拟的,所以用postman这个工具:

成功显示,说明controller层方法成功的拿到了post请求中的参数

5.2 配置文件的两种写法

1.两种写法

都挺好,可以根据团队规范,或自己喜好,二选一即可:

但不推荐两者都用

  • yml读作 亚美哦
  • 本项目中,采用的是第一种

2.两种写法可以互相转换

https://www.toyaml.com/index.html

3.properties的写法

在配置文件application.properties中:

增加三个配置项

server.port=8081
spring.application.name=first-spring-boot        // 配置项目的名字
server.servlet.context-path=/first                // 配置公共前缀,用于区分不同的项目

启动应用;

浏览器:

这说明上面的配置生效了

4.yml的写法

再将上述配置文件application.properties,改名为配置文件application.yml

加入在线转换的配置信息

server:
  port: 8081
  servlet:
    context-path: /first
spring:
  application:
    name: first-spring-boot

启动应用;

浏览器:

这说明上面的配置也生效了

5.3 配置两种自定义属性(变量)

属性,就是变量的意思

某个经常变的属性,如果,一是不好找,二是不方便改:

1.一般变量的赋值

(1)不好的写法:写死在代码中

(2)正确的写法:

在配置文件application.properties中:

增加年级、班级的配置项

server.port=8081
spring.application.name=first-spring-boot
server.servlet.context-path=/first

school.grade=3
school.classnum=1

在controller控制层的PropertiesController类中:

使用注解@Value,并放在属性上

/**
 *      与配置相关的Controller
 */
@RestController
public class PropertiesController {

    @Value("${school.grade}")               // 用元数据注解来赋值:将方法属性与前面配置项进行绑定
    private Integer grade;

    @Value("${school.classnum}")
    private Integer classnum;


    @GetMapping("/gradeclass")
    public String gradeClass(){
        return "年级:" + grade + "班级:" + classnum;
    }


}

上述使用的注解,其实是元数据注解中的一个,旨在提供辅助信息

见21.3章节:

2.静态变量的赋值

与之前一般的属性的不同:

正确的写法:

使用注解@Value,放在方法上;

同时,再用自动生成的set方法,对静态变量进行赋值

/**
 *      与配置相关的Controller
 */
@RestController
public class PropertiesController {

    @Value("${school.grade}")               // 指定的配置项的名字
    private Integer grade;

    @Value("${school.classnum}")
    private Integer classnum;

    

    static Integer age;

    @Value("${school.age}")
    public void setAge(Integer age) {       // 声明里面没有static
        PropertiesController.age = age;
    }


    

    @GetMapping("/gradeclass")
    public String gradeClass(){
        return "年级:" + grade + "班级:" + classnum;
    }


    @GetMapping("/static")
    public String staticPara(){
        return "静态变量的值:" + age;
    }


}

我的问题:

类变量,通过set方法赋值,核心原理是什么?

自己答:难道是类变量比实例变量的级别高?

浏览器:

成功显示了静态变量的值

关于interface接口、API接口:

对比interface接口API接口
含义是面向对象编程语言中,接口操作的关键字Application Programming Interface,应用程序编程接口
本质把所需的成员组合起来,用来封装一定功能的集合作为预先定义的函数(方法),你无需访问源码,或理解内部工作字细节,用户直接用即可

六、学生信息查询小案例:编写Service层、DAO层

目标:把整个Spring Boot项目,从controller层、Service层、DAO层,打通链路

6.1 引入依赖

引入两个与数据库相关的依赖

<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.2.1.RELEASE</version>                            <!--1.这里更改版本-->
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.imooc</groupId>
    <artifactId>spring-boot-learn</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>spring-boot-learn</name>
    <description>Demo project for Spring Boot</description>

    <properties>
        <java.version>1.8</java.version>        <!--这里的Java版本是1.8-->
    </properties>
    <!--2.阿里云Maven镜像-->
    <repositories>
        <repository>
            <id>aliyun</id>
            <name>aliyun</name>
            <url>https://maven.aliyun.com/repository/public</url>
        </repository>
    </repositories>
    <pluginRepositories>
        <pluginRepository>
            <id>aliyun</id>
            <name>aliyun</name>
            <url>https://maven.aliyun.com/repository/public</url>
        </pluginRepository>
    </pluginRepositories>

    <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>
        <!--1.用于将Java代码,转换为数据库可以识别的语句-->
        <dependency>
            <groupId>org.mybatis.spring.boot</groupId>
            <artifactId>mybatis-spring-boot-starter</artifactId>
            <version>2.1.1</version>
        </dependency>
        <!--2.用于连接数据库-->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
        </dependency>

    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <version>2.2.1.RELEASE</version>                     <!--3.这里加上版本信息,否则会出错-->
            </plugin>
        </plugins>
    </build>

</project>

6.2 新建数据库(表)

打开数据库可视化工具:

新建数据库interview

在上述数据库中,新建数据表students

6.3 编写实体类

package com.imooc.springbootlearn.pojo;

/**
 * 学生实体类
 */
public class Student {

    private Integer id;
    private String name;

    public Student() {
    }

    public Student(Integer id, String name) {       // 全参的构造方法
        this.id = id;
        this.name = name;
    }

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

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

    @Override
    public String toString() {
        return "Student{" +
                "id=" + id +
                ", name='" + name + '\'' +
                '}';
    }
}

6.4 编写配置文件application.properties

最下面的是数据库的连接信息

server.port=8081
spring.application.name=first-spring-boot
server.servlet.context-path=/first


spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/interview?serverTimezone=UTC&useUnicode=true&characterEncoding=utf-8&useSSL=true
spring.datasource.username=root
spring.datasource.password=1234abcd

6.5 mapper层

在mapper层中,新建接口StudentMapper

/**
 *     查询学生信息mapper
 */
@Mapper                                 // 等效于xml配置文件的mapper标签,是MyBatis框架提供的注解,用户创建该接口的实现类
@Repository                             // 被Spring IoC识别到,这是mapper类,进行自动的实例化对象、管理对象
public interface StudentMapper {

    @Select("SELECT * FROM students WHERE id=#{id}")    // sql语句直接源码中
    public Student findById(Integer id);       // 职能:从数据库中,根据id查询student


}
  • 其实就是把原先XML中哪些配置项,直接硬搬进来了
  • 注解@Mapper:是MyBatis框架提供的注解,用于自动创建该mapper接口的实现类

关于上述使用的组件式注解:

见21.3章节:

6.6 service层

在service层中,新建类StudentService

调用上面的接口

/**
 *    查询学生信息service
 */
@Service
public class StudentService {

    @Autowired                                   // 根据类型依赖注入、属性赋值
    StudentMapper studentMapper;


    public Student getStudent(Integer id) {
        return studentMapper.findById(id);      // 利用mapper进行数据库的操作
    }


}

6.7 controller层

controller层中,新建类StudentController

/**
 *      学生Controller
 */
@RestController
public class StudentController {

    @Resource                                   // 根据名称依赖注入、属性赋值
    private StudentService studentService;


    @GetMapping("/student")
    public String requestPara(@RequestParam Integer id) {        // 注解@RequestParam,用于自动接收get请求问号?后的参数
        return studentService.getStudent(id).toString();
    }

}

关于上述使用的两种装配式注解:

见21.3章节:

6. 8 结果

启动主启动类:

真简洁

@SpringBootApplication
public class SpringBootLearnApplication {           // 主启动类

    public static void main(String[] args) {        // 主方法
        SpringApplication.run(SpringBootLearnApplication.class, args);
    }

}

浏览器:

这说明成功查询到了学生信息:

综上所述,已经跑通了Spring Boot框架的整个开发流程。

相比以前,确实简化了很多。

声明:Jerry's Blog|版权所有,违者必究|如未注明,均为原创|本网站采用BY-NC-SA协议进行授权

转载:转载请注明原文链接 - 25.1 Spring Boot基础


Follow excellence, and success will chase you.