springboot+thymeleaf modelandview解析异常_099 SpringBoot异常处理与单元测试、数据校验、热部署...

SpringBoot 中异常处理与单元测试

1. 异常处理

SpringBoot 中对于异常处理提供了五种处理方式

package com.sxt.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.servlet.ModelAndView;

@Controller
public class UserController {

    @RequestMapping("showInfo")
    public String showInfo(){
        String str = null;
        System.out.println(str.length());
        return "success";
    }

}

1.1自定义错误页面

SpringBoot 默认的处理异常的机制:SpringBoot默认的已经提供了一套处理异常的机制。一旦程序中出现了异常 SpringBoot 会向/error 的 url 发送请求。在 SpringBoot 中提供了一个名为 BasicErrorController 来处理/error 请求,然后跳转到默认显示异常的页面来展示异常信息。

如 果 我 们 需 要 将 所 有 的 异 常 同 一 跳 转 到 自 定 义 的 错 误 页 面 , 需 要 在 src/main/resources/templates 目录下创建 error.html 页面。注意:页面名称必须叫 error

cdeb0ba108284e71cc36265fb24eeb55.png

1.2 通过@ExceptionHandler 注解处理异常

package com.sxt.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.servlet.ModelAndView;

@Controller
public class UserController {

    @RequestMapping("showInfo")
    public String showInfo(){
        String str = null;
        System.out.println(str.length());
        return "success";
    }

    @ExceptionHandler(value = {java.lang.NullPointerException.class})
    public ModelAndView exception01(Exception e){
        ModelAndView mv = new ModelAndView();
        mv.addObject("errorMessage1",e.toString());
        mv.setViewName("error01");
        return mv;
    }

}

创建页面(error01.html):

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html xmlns:th="http://www.thymeleaf.org">
<head>
    <meta charset="UTF-8">
    <title>错误处信息页面</title>
</head>
<body>
    出错了......<br/>
    错误信息:
    <span th:text="${errorMessage1}"/>
</body>
</html>

1.3 通过@ControllerAdvice 与@ExceptionHandler 注解处理异常

1.3.1创建全局异常处理类

package com.sxt.exception;

import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.servlet.ModelAndView;

/**
 * 全局异常处理类:
 *      缺点:当异常过多时,方法的书写量大
 */
//@ControllerAdvice
public class GlobalException {

    @ExceptionHandler(value = {java.lang.NullPointerException.class})
    public ModelAndView exception01(Exception e){
        ModelAndView mv = new ModelAndView();
        mv.addObject("errorMessage1",e.toString());
        mv.setViewName("error01");
        return mv;
    }

    @ExceptionHandler(value = {java.lang.ArithmeticException.class})
    public ModelAndView exception02(Exception e){
        ModelAndView mv = new ModelAndView();
        mv.addObject("errorMessage2",e.toString());
        mv.setViewName("error02");
        return mv;
    }

}

1.4 通过 SimpleMappingExceptionResolver 对象处理异常

1.4.1 创建全局异常处理类

package com.sxt.exception;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.handler.SimpleMappingExceptionResolver;

import java.util.Properties;

/**
 * 全局异常处理类:
 *      通过 SimpleMappingExceptionResolver 对象处理异常
 *   缺点:不能够传递异常信息
 */
//@Configuration
public class GlobalException2 {

    @Bean
    public SimpleMappingExceptionResolver getSimpleMappingExceptionResolver(){
        SimpleMappingExceptionResolver resolver = new SimpleMappingExceptionResolver();
        Properties properties = new Properties();
        /**
         * 参数一:异常类型,并且是全名
         * 参数二:跳转的视图名称
         */
        properties.setProperty("java.lang.NullPointerException","error03");
        properties.setProperty("java.lang.ArithmeticException","error04");
        resolver.setExceptionMappings(properties);
        return resolver;
    }

}

1.5 通过自定义 HandlerExceptionResolver 对象处理异常 (常用)

1.5.1 创建全局异常处理类

package com.sxt.exception;

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.HandlerExceptionResolver;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * 全局异常处理类:
 *      通过自定义 HandlerExceptionResolver 对象处理异常
 *      必须要实现 HandlerExceptionResolver
 */
@Configuration
public class GlobalException3 implements HandlerExceptionResolver {
    @Override
    public ModelAndView resolveException(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) {
        ModelAndView mv = new ModelAndView();
        // 判断不同异常类型,做不同视图的跳转
        if (ex instanceof NullPointerException) {
            mv.setViewName("error05");
        }
        if (ex instanceof ArithmeticException) {
            mv.setViewName("error06");
        }
        mv.addObject("error",ex.toString());
        return mv;
    }
}

2. Spring Boot 整合 Junit 单元测试

SpringBoot2.0之前使用Junit3/4进行测试

SpringBoot2.x 使用 Junit5 作为测试平台

2.1 修改 POM 文件添加 Test 启动器

       <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
            <exclusions>
                <exclusion>
                    <groupId>org.junit.vintage</groupId>
                    <artifactId>junit-vintage-engine</artifactId>
                </exclusion>
            </exclusions>
        </dependency>

49012122dc19067958e9a2d56a9e9a81.png

Spring Boot 服务端数据校验

1、 Spring Boot 对实体对象的校验

1.1 搭建项目环境

f65b71644a7db475cc198bedf09ee370.png
<?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>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.sxt</groupId>
    <artifactId>1126-02-springboot-datacheck</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>1126-02-springboot-datacheck</name>
    <description>Demo project for Spring Boot</description>

    <properties>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-thymeleaf</artifactId>
        </dependency>
        <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>
            <exclusions>
                <exclusion>
                    <groupId>org.junit.vintage</groupId>
                    <artifactId>junit-vintage-engine</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
    </dependencies>

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

</project>

1.1.1 创建实体(get、set方法):

public class Users {
    private Integer userid;
    private String username;
    private String usersex;
}

1.1.2 创建controller方法:

@RequestMapping("/user")
public class UserController {

    /**
     * 添加用户
     */
    @RequestMapping("/addUser")
    public String addUser(Users users){
        System.out.println(users);
        return "success";
    }

}

1.1.3 创建页面:

addUser.html:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html xmlns:th="http://www.thymeleaf.org">
    <link rel="shortcut icon" href="../resources/favicon.ico" th:href="@{/static/favicon.ico}"/>
    <title>添加用户</title>
</head>
<body>
    <form th:action="@{/user/addUser}" method="post">
        用户名称:<input type="text" name="username" />
        用户性别:<input type="text" name="usersex" />
        <input type="submit" value="添加" />
    </form>
</body>
</html>

success.html:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>处理请求成功页面</title>
</head>
<body>
    请求成功.....
</body>
</html>

70ecc0176d62245be45946f4a5cbde8d.png

1.2 对实体对象做数据校验

1.2.1Spring Boot 数据校验的技术特点

Spring Boot 中使用了 Hibernate-validator 校验框架。

1.2.2对实体对象数据校验步骤

1.2.2.1 修改实体类添加校验规则

package com.sxt.pojo;

import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;

/**
 *  @NotNull: 对基本数据类型的对象类型做非空校验
 *  @NotBlank: 对字符串类型做非空校验
 *  @NotEmpty: 对集合类型做非空校验
 */
public class Users {

    @NotNull
    private Integer userid;
    @NotBlank
    private String username;
    @NotBlank
    private String usersex;

    @Override
    public String toString() {
        return "Users{" +
                "userid=" + userid +
                ", username='" + username + ''' +
                ", usersex='" + usersex + ''' +
                '}';
    }

    public Integer getUserid() {
        return userid;
    }

    public void setUserid(Integer userid) {
        this.userid = userid;
    }

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getUsersex() {
        return usersex;
    }

    public void setUsersex(String usersex) {
        this.usersex = usersex;
    }
}

1.2.2.2 在 Controller 中开启校验(@Validated)

package com.sxt.controller;

import com.sxt.pojo.Users;
import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.validation.FieldError;
import org.springframework.validation.ObjectError;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.RequestMapping;

import java.util.List;

@Controller
@RequestMapping("/user")
public class UserController {

    /**
     * 添加用户
     */
    @RequestMapping("/addUser")
    public String addUser(@Validated Users users, BindingResult result){
        if (result.hasErrors()) {
            List<ObjectError> list = result.getAllErrors();
            for (Object err : list) {
                FieldError fieldError = (FieldError)err;
                String errName = fieldError.getField();
                String message = fieldError.getDefaultMessage();
                System.out.println(errName+"  "+message);
            }
            return "addUser";
        }
        System.out.println(users);
        return "success";
    }

}

dbf97939469f25ccd53c7768ca8b0939.png

4909a44b0700bb7ba74fa7b3a24eb223.png

1.2.2.3 在页面中获取提示信息

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html xmlns:th="http://www.thymeleaf.org">
    <link rel="shortcut icon" href="../resources/favicon.ico" th:href="@{/static/favicon.ico}"/>
    <title>添加用户</title>
</head>
<body>
    <form th:action="@{/user/addUser}" method="post">
        用户名称:<input type="text" name="username" />
            <font color="red"><span th:errors="${users.username}"></span></font><br/>
        用户性别:<input type="text" name="usersex" />
            <font color="red"><span th:errors="${users.usersex}"></span></font><br/>
        <input type="submit" value="添加" />
    </form>
</body>
</html>

f395e9d7d712f915a71afbb01c7e1c88.png

1.2.3自定义错误提示信息 (两种方式)

1.2.3.1 在注解中定义提示信息 (硬编码,不方便修改)

package com.sxt.pojo;

import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;

/**
 *  @NotNull: 对基本数据类型的对象类型做非空校验
 *  @NotBlank: 对字符串类型做非空校验
 *  @NotEmpty: 对集合类型做非空校验
 */
public class Users {

    @NotNull(message = "用户ID不能为空")
    private Integer userid;
    @NotBlank(message = "用户名称不能为空")
    private String username;
    @NotBlank(message = "用户性别不能为空")
    private String usersex;

    @Override
    public String toString() {
        return "Users{" +
                "userid=" + userid +
                ", username='" + username + ''' +
                ", usersex='" + usersex + ''' +
                '}';
    }

    public Integer getUserid() {
        return userid;
    }

    public void setUserid(Integer userid) {
        this.userid = userid;
    }

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getUsersex() {
        return usersex;
    }

    public void setUsersex(String usersex) {
        this.usersex = usersex;
    }
}

0c48c02cf03ed627e2c00fd9c504714f.png

33ad9ce505264ba322b29e3a06809427.png

1.2.3.2 在配置文件中定义提示信息(resources目录下 便于修改)

配置文件名必须是 ValidationMessages.properties

44cf4ce3296910f95a3bc16c81c67852.png
userid.notnull=用户ID不能为空
username.notnull=用户名称不能为空
usersex.notnull=用户性别不能为空

在实体类中引入:

package com.sxt.pojo;

import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;

/**
 *  @NotNull: 对基本数据类型的对象类型做非空校验
 *  @NotBlank: 对字符串类型做非空校验
 *  @NotEmpty: 对集合类型做非空校验
 */
public class Users {

    @NotNull(message = "{userid.notnull}")
    private Integer userid;
    @NotBlank(message = "{username.notnull}")
    private String username;
    @NotBlank(message = "{usersex.notnull}")
    private String usersex;

    @Override
    public String toString() {
        return "Users{" +
                "userid=" + userid +
                ", username='" + username + ''' +
                ", usersex='" + usersex + ''' +
                '}';
    }

    public Integer getUserid() {
        return userid;
    }

    public void setUserid(Integer userid) {
        this.userid = userid;
    }

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getUsersex() {
        return usersex;
    }

    public void setUsersex(String usersex) {
        this.usersex = usersex;
    }
}

f6a2e9a9035dfd6b2a6816c319c0bd26.png

出现乱码问题,解决方法:

原因:配置文件的编码集是使用ISO-8859-1进行编码

转码方式:使用jdk自带的native2ascii.exe转换为对应的字节文件

使用方法:

C:UsersLenovo>cd "C:Program FilesJavajdk1.8.0_91bin

C:Program FilesJavajdk1.8.0_91bin>native2ascii.exe E:/aa.txt E:/bb.txt

1395f42e1d6ece2e58bf5a4002e24cd1.png
userid.notnull=u7528u6237Idu4e0du80fdu4e3au7a7a
username.notnull=u7528u6237u59d3u540du4e0du80fdu4e3au7a7a
usersex.notnull=u7528u6237u6027u522bu4e0du80fdu4e3au7a7a

d53f22e09a0479a4ae6338f3954a222d.png

1.2.4解决页面页面的controller:

package com.sxt.controller;

import com.sxt.pojo.Users;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
public class PageController {

    @RequestMapping("/{page}")
    public String showPage(@PathVariable String page){
        return page;
    }

}

9e1d3327b052c017c52e23d666f89c70.png

解决方法:

在跳转页面的方法中注入一个对象,要求参数对象的变量名必须是对象类型名称首字母小写格式。

package com.sxt.controller;

import com.sxt.pojo.Users;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;

/**
 * 跳转页面方法
 * 解决异常的方式:可以在跳转页面的方法中注入一个 Users 对象
 * 由于 SprignMVC 会将该对象放入到 Model 中传递,key 的名称会使用该对象的驼峰命名规则来作为 key
 */
@Controller
public class PageController {

    @RequestMapping("/{page}")
    public String showPage(@PathVariable String page, Users users){
        return page;
    }

}

81299d2ff3278ee96cda4bcd779145f3.png

1.2.5 修改参数 key 的名称 (使用@ModelAttribute

PageController:

package com.sxt.controller;

import com.sxt.pojo.Users;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;

/**
 * 跳转页面方法
 * 解决异常的方式:可以在跳转页面的方法中注入一个 Users 对象
 * 由于 SprignMVC 会将该对象放入到 Model 中传递,key 的名称会使用该对象的驼峰命名规则来作为 key
 */
@Controller
public class PageController {

    @RequestMapping("/{page}")
    public String showPage(@PathVariable String page,@ModelAttribute("aa") Users users){
        return page;
    }

}

UserController:

package com.sxt.controller;

import com.sxt.pojo.Users;
import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.validation.FieldError;
import org.springframework.validation.ObjectError;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;

import java.util.List;

@Controller
@RequestMapping("/user")
public class UserController {

    /**
     * 添加用户
     */
    @RequestMapping("/addUser")
    public String addUser(@ModelAttribute("aa") @Validated Users users, BindingResult result){
        if (result.hasErrors()) {
            List<ObjectError> list = result.getAllErrors();
            for (Object err : list) {
                FieldError fieldError = (FieldError)err;
                String errName = fieldError.getField();
                String message = fieldError.getDefaultMessage();
                System.out.println(errName+"  "+message);
            }
            return "addUser";
        }
        System.out.println(users);
        return "success";
    }

}

addUser.html:

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html xmlns:th="http://www.thymeleaf.org">
    <link rel="shortcut icon" href="../resources/favicon.ico" th:href="@{/static/favicon.ico}"/>
    <title>添加用户</title>
</head>
<body>
    <form th:action="@{/user/addUser}" method="post">
        用户名称:<input type="text" name="username" />
            <font color="red"><span th:errors="${aa.username}"></span></font><br/>
        用户性别:<input type="text" name="usersex" />
            <font color="red"><span th:errors="${aa.usersex}"></span></font><br/>
        <input type="submit" value="添加" />
    </form>
</body>
</html>

c787c715434257c6fbb45f9e44a9eed9.png

74e8b663cbd7496ae1b43db7ba8f5558.png

1.2.6 其他校验规则

@NotNull: 判断基本数据类型的对象类型是否为 null

@NotBlank: 判断字符串是否为 null 或者是空串(去掉首尾空格)。

@NotEmpty: 判断集合是否为空。

@Length: 判断字符的长度(最大或者最小)

@Min: 判断数值最小值

@Max: 判断数值最大值

@Email: 判断邮箱是否合法

de228d16b77d862d6d7fb40e598fde20.png

2. Spring Boot 对 Controller 中其他参数的校验

2.1 编写页面 (findUser.html)

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html xmlns:th="http://www.thymeleaf.org">
    <link rel="shortcut icon" href="../resources/favicon.ico" th:href="@{/static/favicon.ico}"/>
    <title>添加用户</title>
</head>
<body>
    <form th:action="@{/user/findUser}" method="post">
        用户名称:<input type="text" name="username" />
        <input type="submit" value="查询" />
    </form>
</body>
</html>

请求方法:

    @PostMapping("/findUser")
    public String findUser(@NotBlank String username){
        System.out.println(username);
        return "success";
    }

09137a14842fa76fb6ffaa42cb0cfed8.png

点击查询后:

8ba7e0646306856328a0ac8d88d344e3.png

2.2 对参数指定校验规则 ,并在 Controller 中开启校验

package com.sxt.controller;

import com.sxt.pojo.Users;
import org.springframework.stereotype.Controller;
import org.springframework.validation.BindingResult;
import org.springframework.validation.FieldError;
import org.springframework.validation.ObjectError;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;

import javax.validation.constraints.NotBlank;
import java.util.List;

@Controller
@RequestMapping("/user")
@Validated
public class UserController {

    /**
     * 添加用户
     */
    @RequestMapping("/addUser")
    public String addUser( @Validated Users users, BindingResult result){
//    public String addUser(@ModelAttribute("aa") @Validated Users users, BindingResult result){
        if (result.hasErrors()) {
            List<ObjectError> list = result.getAllErrors();
            for (Object err : list) {
                FieldError fieldError = (FieldError)err;
                String errName = fieldError.getField();
                String message = fieldError.getDefaultMessage();
                System.out.println(errName+"  "+message);
            }
            return "addUser";
        }
        System.out.println(users);
        return "success";
    }

    @PostMapping("/findUser")
    public String findUser(@NotBlank String username){
        System.out.println(username);
        return "success";
    }

}

d77cc43ec52df280962bbcf55f1d1189.png

e17fd6a141329cc82ecebeb5ad35a4b2.png

点击查询后:

1519a37bf0a0cb01b6b272585d4a8070.png

2.3 通过全局异常处理来跳转页面

package com.sxt.exception;

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.HandlerExceptionResolver;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.validation.ConstraintViolationException;

@Configuration
public class GlobalException implements HandlerExceptionResolver {
    @Override
    public ModelAndView resolveException(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) {
        ModelAndView mv = new ModelAndView();
        // 判断不同异常类型,做不同视图的跳转
        if (ex instanceof NullPointerException) {
            mv.setViewName("error05");
        }
        if (ex instanceof ArithmeticException) {
            mv.setViewName("error06");
        }
        if(ex instanceof ConstraintViolationException) {
            mv.setViewName("findUser");
        }
        mv.addObject("error",ex.getMessage().split(":")[1]);
        return mv;
    }
}

findUser.html页面(接收信息):

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html xmlns:th="http://www.thymeleaf.org">
    <link rel="shortcut icon" href="../resources/favicon.ico" th:href="@{/static/favicon.ico}"/>
    <title>添加用户</title>
</head>
<body>
    <form th:action="@{/user/findUser}" method="post">
        用户名称:<input type="text" name="username" />
            <span style="color: red" th:text="${error}"/><br/>
        <input type="submit" value="查询" />
    </form>
</body>
</html>

5ea8b7788e8f398bfeff63dc9ba8b074.png

点击查询后:

eb9616695d4fa2256eb8c439db1afaba.png

可设置错误提示信息:

a3c7024f4a76bbdad1ddff597fe7d98d.png

Spring Boot 热部署

1 通过 DevTools 工具实现热部署

1.1修改 POM 文件,添加 DevTools 依赖

        <!-- 热部署依赖 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <optional>true</optional>
        </dependency>

1.2配置 Idea

1.2.1设置自动编译 (Ctrl+Alt+s)

f9c19b6105f50f3e21a381b04162e3b4.png

1.2.2设置 Idea 的 Registry

通过快捷键打开该设置项:Ctrl+Shift+Alt+/

勾选 complier.automake.allow.when.app.running

1d9145bb27be5de33773558f12051a2d.png

1a5f3fee1d77e43f08d466c9da59856d.png
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值