当前位置: 首页>数据库>正文

springboot 页面显示 springboot错误页面


文章目录

  • springboot默认的错误处理机制
  • 默认效果
  • 定制错误响应页面
  • 如何定制错误页面(有模板的情况下)
  • 没有模板的情况下
  • 以上都没有错误页面,则直接进入到bootstrap默认错误页面
  • 自定义异常类并抛出异常
  • 如何定制错误的json数据页面(其他客户端访问)
  • 自定义异常&返回定制的json数据
  • 增加自适应
  • 将定制的数据带出去
  • 如何将异常处理器中的错误信息进行显示


springboot默认的错误处理机制

默认效果

1、直接返回错误信息,状态码等,404

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_spring,第1张

2、如果是其他客户端,默认响应一个json数据

定制错误响应页面

如何定制错误页面(有模板的情况下)
  • 有模板的情况下;将错误页面命名为错误状态码.html,放在模板引擎文件夹里面的error文件夹下,发生此状态的错误,就会来到对应的页面。
  • 可以使用4xx、5xx作为错误页面的文件名来匹配这种类型的错误,优先匹配具体错误代码,如果没有,则使用代号页面

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_spring_02,第2张

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_java_03,第3张

  • 页面中可以获取的信息:(defaultErrorAttributes.java)
  • timestamp:时间戳
  • status:状态码
  • error:错误提示
  • Exception:异常对象
  • message:异常消息
  • errors:jsr303数据校验的错误都在这里
  • 获取方式
  • 使用行内表达式

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_spring_04,第4张

没有模板的情况下
  • 在static文件下下添加error文件下,具体错误页面命名和有模板时一样,但是没有模板的渲染
以上都没有错误页面,则直接进入到bootstrap默认错误页面

自定义异常类并抛出异常

  • 先写一个异常类:
package springbootdemo.exception;

public class UserNotExistException extends RuntimeException{
    public UserNotExistException() {
        super("用户不存在");
    }
}
  • 在某个请求中抛出异常
package springbootdemo.controller;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import springbootdemo.exception.UserNotExistException;

@Controller
public class HelloController {
    @ResponseBody
    @GetMapping("/hello")
    public String hello(@RequestParam("user") String user){
        //在hello请求中获取user的值
        //当值等于admin的时候,抛出异常
        if ("admin".equals(user)) {
            throw new UserNotExistException();
        }
        return "hello,world";
    }
}
  • 定制html页面,显示异常信息
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<h2>status:[[${status}]]</h2>
<h2>timestamp:[[${timestamp}]]</h2>
  <!--显示异常信息-->
<h2>message:[[${message}]]</h2>
  <!--显示异常对象-->
<h2>exception:[[${exception}]]</h2>
</body>
</html>

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_springboot 页面显示_05,第5张

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_错误页面_06,第6张

如何定制错误的json数据页面(其他客户端访问)

自定义异常&返回定制的json数据

没有自适应,无论在浏览器端还是其他移动端,都显示一样的数据

  • 创建一个异常处理类
package springbootdemo.controller;

import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import springbootdemo.exception.UserNotExistException;

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

@ControllerAdvice
public class MyExceptionHandler {
    @ResponseBody
    //出现异常时,springmvc将会把这个调用这个方法来处理异常
  	//注解表上要处理哪些异常
    @ExceptionHandler({UserNotExistException.class})
    public Map<String, Object> handlerException(Exception e){
        Map<String,Object> map = new HashMap<>();
      //定制返回信息,使用json格式
        map.put("code","user not exist");
        map.put("message",e.getMessage());
        return map;
        }
}

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_状态码_07,第7张

增加自适应

basicErrorController类可以处理/error请求,/error请求是自适应的

/error请求自适应:如果浏览器页面,则显示错误页面,如果是其他客户端,则显示json数据

  • 修改异常处理方法
@ExceptionHandler({UserNotExistException.class})
public String handlerException(Exception e){
    Map<String,Object> map = new HashMap<>();
    map.put("code","user not exist");
    map.put("message",e.getMessage());
    //转发到/error,让它来帮助进行自适应
    return "forward:/error";
}
  • 缺陷还是存在,出现错误之后又到了默认空白页面
  • 原因:错误视图没有解析到
  • 错误页面中错误状态码都为200,不是属于错误状态码
  • 解决方法:传入自己的错误状态码,不传递默认为200
//basicErrorController类中进行错误状态码的设置
HttpStatus status = this.getStatus(request);
if (status == HttpStatus.NO_CONTENT) {
    return new ResponseEntity(status);
} else {
    Map<String, Object> body = this.getErrorAttributes(request, this.getErrorAttributeOptions(request, MediaType.ALL));
    return new ResponseEntity(body, status);
}
@ExceptionHandler({UserNotExistException.class})
    public String handlerException(Exception e, HttpServletRequest request){
        Map<String,Object> map = new HashMap<>();
        //设置自己的错误状态码,默认为200,不会进入错误页面的解析流程,应该自己设置状态码
        /**
         * 在AbstractErrorController中使用如下方式设置错误状态码
         *Integer statusCode = (Integer)request.getAttribute("javax.servlet.error.status_code");
         */
        request.setAttribute("javax.servlet.error.status_code",500);
        map.put("code","user not exist");
        map.put("message",e.getMessage());
        //转发到/error,让它来帮助进行自适应
        return "forward:/error";
    }

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_spring_08,第8张

  • 解决了自适应的问题,但是我们自己带入的错误数据没有显示(map.put("code","user not exist"); map.put("message",e.getMessage());
将定制的数据带出去

出现错误之后,会来到/error请求,会被basicErrorController类处理,响应出去可以获取的数据是由类中调用了abstractErrorController类(basicErrorController的父类,ErrorController的子类)中的getErrorAttributes()方法获取的。

basicErrorController(使用了@ConditionalOnMissingBean)在springboot中属于默认处理error请求的类,在没有自定义的情况下,默认使用

  • 解决方法
  • 完全编写一个ErrorController类(或者abstractErrorController),放在容器中
  • 页面上能用的数据,或者是json返回能用的数据都是通过errorAttributes(使用了@ConditionalOnMissingBean).getErrorAttributes得到的,
    在springboot中,就是使用defaultErrorAttributes.getErrorAttributes默认进行数据处理,所以,可以自定义一个MyErrorAttributes类
/**
 * 在容器中添加自定义的errorattributes,来定制返回信息
 */
@Component
public class MyErrorAttributes  extends DefaultErrorAttributes {
    @Override
    public Map<String, Object> getErrorAttributes(WebRequest webRequest, ErrorAttributeOptions options) {
        Map<String, Object> map = super.getErrorAttributes(webRequest, options);
        //在这个map中添加自己的错误信息
        map.put("author","Zer0");
        return map;
    }
}

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_springboot 页面显示_09,第9张

如何将异常处理器中的错误信息进行显示
  • 将异常处理器中的信息传递给自定义的errorattribute类中
@ExceptionHandler({UserNotExistException.class})
public String handlerException(Exception e, HttpServletRequest request){
    Map<String,Object> map = new HashMap<>();
    //设置自己的错误状态码,默认为200,不会进入错误页面的解析流程,应该自己设置状态码
    /**
     * 在AbstractErrorController中使用如下方式设置错误状态码
     *Integer statusCode = (Integer)request.getAttribute("javax.servlet.error.status_code");
     */
    request.setAttribute("javax.servlet.error.status_code",500);
    map.put("code","user not exist");
    map.put("message",e.getMessage());

    //将map放到request域中,通过setarttibutes方法进行设置
    request.setAttribute("ext",map);
    //转发到/error,让它来帮助进行自适应,同时将map带过去
    return "forward:/error";
}
  • 在MyErrorAttribute类中进行接收
public class MyErrorAttributes  extends DefaultErrorAttributes {
    @Override
    public Map<String, Object> getErrorAttributes(WebRequest webRequest, ErrorAttributeOptions options) {
        //这个map是页面和json获取的所有字段
        Map<String, Object> map = super.getErrorAttributes(webRequest, options);
        //在这个map中添加自己的错误信息
        map.put("author","Zer0");
        /**
         * 通过webRequest(封装之后的requestattribute)对象的getAttribute方法获取异常处理器中的信息
         * 两个参数:
         *  第一个是要获取的数据名
         *  第二个表上从哪里获取数据(session(1)、request(0))
         */
        Map<String,Object> ext = (Map<String, Object>) webRequest.getAttribute("ext", 0);
        //将信息合并
        map.put("ext",ext);
        return map;
    }

springboot 页面显示 springboot错误页面,springboot 页面显示 springboot错误页面_状态码_10,第10张



https://www.xamrdz.com/database/67s1939696.html

相关文章: