Web之异步请求-拦截器-异常处理

本文介绍了跨域访问的概念及解决方法,包括使用@CrossOrigin注解实现跨域支持;同时详细讲解了拦截器的工作原理及其配置过程;还探讨了异常处理机制,包括自定义异常与异常处理器的实现。

异步请求-跨域访问

跨域访问介绍

  • 当通过域名A下的操作访问域名B下的资源时,称为跨域访问

  • 跨域访问时,会出现无法访问的现象

 跨域环境搭建

  • 为当前主机添加备用域名

    • 修改windows安装目录中的host文件

    • 格式: ip 域名

  • 动态刷新DNS

    • 命令: ipconfig /displaydns

    • 命令: ipconfig /flushdns

 跨域访问支持

 名称: @CrossOrigin  类型: 方法注解 、 类注解  位置:处理器类中的方法上方 或 类上方  作用:设置当前处理器方法/处理器类中所有方法支持跨域访问  范例:

@RequestMapping("/cross")
@ResponseBody
//使用@CrossOrigin开启跨域访问
//标注在处理器方法上方表示该方法支持跨域访问
//标注在处理器类上方表示该处理器类中的所有处理器方法均支持跨域访问
@CrossOrigin
public User cross(HttpServletRequest request){
    System.out.println("controller cross..."+request.getRequestURL());
    User user = new User();
    user.setName("Jockme");
    user.setAge(39);
    return user;
}

 拦截器

拦截器概念

  • 请求处理过程解析

 拦截器( Interceptor)是一种动态拦截方法调用的机制  作用:

  1. 在指定的方法调用前后执行预先设定后的的代码

  2. 阻止原始方法的执行

 核心原理: AOP思想  拦截器链:多个拦截器按照一定的顺序,对原始被调用功能进行增强

  • 拦截器VS过滤器  归属不同: Filter属于Servlet技术, Interceptor属于SpringMVC技术  拦截内容不同: Filter对所有访问进行增强, Interceptor仅针对SpringMVC的访问进行增强

自定义拦截器开发过程

  • 实现HandlerInterceptor接口

    //自定义拦截器需要实现HandleInterceptor接口
    public class MyInterceptor implements HandlerInterceptor {
        //处理器运行之前执行
        @Override
        public boolean preHandle(HttpServletRequest request,
                                 HttpServletResponse response,
                                 Object handler) throws Exception {
            System.out.println("前置运行----a1");
            //返回值为false将拦截原始处理器的运行
            //如果配置多拦截器,返回值为false将终止当前拦截器后面配置的拦截器的运行
            return true;
        }
    ​
        //处理器运行之后执行
        @Override
        public void postHandle(HttpServletRequest request,
                               HttpServletResponse response,
                               Object handler,
                               ModelAndView modelAndView) throws Exception {
            System.out.println("后置运行----b1");
        }
    ​
        //所有拦截器的后置执行全部结束后,执行该操作
        @Override
        public void afterCompletion(HttpServletRequest request,
                                    HttpServletResponse response,
                                    Object handler,
                                    Exception ex) throws Exception {
            System.out.println("完成运行----c1");
        }
    ​
        //三个方法的运行顺序为    preHandle -> postHandle -> afterCompletion
        //如果preHandle返回值为false,三个方法仅运行preHandle
    }
  • 配置拦截器

    配置拦截器

<mvc:interceptors>
    <mvc:interceptor>
        <mvc:mapping path="/showPage"/>
        <bean class="com.itheima.interceptor.MyInterceptor"/>
    </mvc:interceptor>
</mvc:interceptors>

注意:配置顺序为先配置执行位置,后配置执行类

 拦截器执行流程

 拦截器配置与方法参数

 前置处理方法

原始方法之前运行

public boolean preHandle(HttpServletRequest request,
                         HttpServletResponse response,
                         Object handler) throws Exception {
    System.out.println("preHandle");
    return true;
}
  • 参数  request:请求对象  response:响应对象  handler:被调用的处理器对象,本质上是一个方法对象,对反射中的Method对象进行了再包装

  • 返回值  返回值为false,被拦截的处理器将不执行

 后置处理方法

原始方法运行后运行,如果原始方法被拦截,则不执行

public void postHandle(HttpServletRequest request,
                       HttpServletResponse response,
                       Object handler,
                       ModelAndView modelAndView) throws Exception {
    System.out.println("postHandle");
}

 参数  modelAndView:如果处理器执行完成具有返回结果,可以读取到对应数据与页面信息,并进行调整

 完成处理方法

拦截器最后执行的方法,无论原始方法是否执行

public void afterCompletion(HttpServletRequest request,
                            HttpServletResponse response,
                            Object handler,
                            Exception ex) throws Exception {
    System.out.println("afterCompletion");
}

 参数  ex:如果处理器执行过程中出现异常对象,可以针对异常情况进行单独处理

 拦截器配置项

<mvc:interceptors>
    <!--开启具体的拦截器的使用,可以配置多个-->
    <mvc:interceptor>
        <!--设置拦截器的拦截路径,支持*通配-->
        <!--/**         表示拦截所有映射-->
        <!--/*          表示拦截所有/开头的映射-->
        <!--/user/*     表示拦截所有/user/开头的映射-->
        <!--/user/add*  表示拦截所有/user/开头,且具体映射名称以add开头的映射-->
        <!--/user/*All  表示拦截所有/user/开头,且具体映射名称以All结尾的映射-->
        <mvc:mapping path="/*"/>
        <mvc:mapping path="/**"/>
        <mvc:mapping path="/handleRun*"/>
        <!--设置拦截排除的路径,配置/**或/*,达到快速配置的目的-->
        <mvc:exclude-mapping path="/b*"/>
        <!--指定具体的拦截器类-->
        <bean class="MyInterceptor"/>
    </mvc:interceptor>
</mvc:interceptors>

 多拦截器配置

责任链模式  责任链模式是一种行为模式  特征: 沿着一条预先设定的任务链顺序执行,每个节点具有独立的工作任务  优势: 独立性:只关注当前节点的任务,对其他任务直接放行到下一节点 隔离性:具备链式传递特征,无需知晓整体链路结构,只需等待请求到达后进行处理即可 灵活性:可以任意修改链路结构动态新增或删减整体链路责任 解耦:将动态任务与原始任务解耦  弊端: 链路过长时,处理效率低下 可能存在节点上的循环引用现象,造成死循环,导致系统崩溃

 异常处理

异常处理器

HandlerExceptionResolver接口(异常处理器)

@Component
public class ExceptionResolver implements HandlerExceptionResolver {
    public ModelAndView resolveException(HttpServletRequest request,
                                         HttpServletResponse response,
                                         Object handler,
                                         Exception ex) {
        System.out.println("异常处理器正在执行中");
        ModelAndView modelAndView = new ModelAndView();
        //定义异常现象出现后,反馈给用户查看的信息
        modelAndView.addObject("msg","出错啦! ");
        //定义异常现象出现后,反馈给用户查看的页面
        modelAndView.setViewName("error.jsp");
        return modelAndView;
    }
}

根据异常的种类不同,进行分门别类的管理,返回不同的信息

public class ExceptionResolver implements HandlerExceptionResolver {
    @Override
    public ModelAndView resolveException(HttpServletRequest request,
                                         HttpServletResponse response,
                                         Object handler,
                                         Exception ex) {
        System.out.println("my exception is running ...."+ex);
        ModelAndView modelAndView = new ModelAndView();
        if( ex instanceof NullPointerException){
            modelAndView.addObject("msg","空指针异常");
        }else if ( ex instanceof  ArithmeticException){
            modelAndView.addObject("msg","算数运算异常");
        }else{
            modelAndView.addObject("msg","未知的异常");
        }
        modelAndView.setViewName("error.jsp");
        return modelAndView;
    }
}

注解开发异常处理器

  • 使用注解实现异常分类管理  名称: @ControllerAdvice  类型: 类注解  位置:异常处理器类上方  作用:设置当前类为异常处理器类  范例:

@Component
@ControllerAdvice
public class ExceptionAdvice {
}  
  • 使用注解实现异常分类管理  名称: @ExceptionHandler  类型: 方法注解  位置:异常处理器类中针对指定异常进行处理的方法上方  作用:设置指定异常的处理方式  范例:  说明:处理器方法可以设定多个

@ExceptionHandler(Exception.class)
@ResponseBody
public String doOtherException(Exception ex){
    return "出错啦,请联系管理员! ";
}  

 异常处理解决方案

  • 异常处理方案

    • 业务异常:  发送对应消息传递给用户,提醒规范操作

    • 系统异常:  发送固定消息传递给用户,安抚用户  发送特定消息给运维人员,提醒维护  记录日志

    • 其他异常:  发送固定消息传递给用户,安抚用户  发送特定消息给编程人员,提醒维护  纳入预期范围内  记录日志

 自定义异常

  • 异常定义格式

    //自定义异常继承RuntimeException,覆盖父类所有的构造方法
    public class BusinessException extends RuntimeException {
        public BusinessException() {
        }
    ​
        public BusinessException(String message) {
            super(message);
        }
    ​
        public BusinessException(String message, Throwable cause) {
            super(message, cause);
        }
    ​
        public BusinessException(Throwable cause) {
            super(cause);
        }
    ​
        public BusinessException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
            super(message, cause, enableSuppression, writableStackTrace);
        }
    }
  • 异常触发方式

    if(user.getName().trim().length()<4) {
        throw new BusinessException("用户名长度必须在2-4位之间,请重新输入! ");
    }
  • 通过自定义异常将所有的异常现象进行分类管理,以统一的格式对外呈现异常消息

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值