范文健康探索娱乐情感热点
投稿投诉
热点动态
科技财经
情感日志
励志美文
娱乐时尚
游戏搞笑
探索旅游
历史星座
健康养生
美丽育儿
范文作文
教案论文
国学影视

SpringBoot如何使用拦截器过滤器监听器?

  过滤器
  过滤器的英文名称为 Filter, 是 Servlet 技术中最实用的技术。
  如同它的名字一样,过滤器是处于客户端和服务器资源文件之间的一道过滤网,帮助我们过滤掉一些不符合要求的请求,通常用作 Session 校验,判断用户权限,如果不符合设定条件,则会被拦截到特殊的地址或者基于特殊的响应。过滤器的使用
  首先需要实现 Filter接口然后重写它的三个方法init 方法:在容器中创建当前过滤器的时候自动调用destory 方法:在容器中销毁当前过滤器的时候自动调用doFilter 方法:过滤的具体操作
  我们先引入 Maven 依赖,其中 lombok 是用来避免每个文件创建 Logger 来打印日志     org.projectlombok     lombok        org.springframework.boot     spring-boot-starter-web 
  我们首先实现接口,重写三个方法,对包含我们要求的四个请求予以放行,将其它请求拦截重定向至/online,只要在将MyFilter实例化后即可,我们在后面整合代码中一起给出。import lombok.extern.log4j.Log4j2; import org.springframework.stereotype.Component;  import javax.servlet.*; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpServletResponseWrapper; import java.io.IOException;  @Log4j2 public class MyFilter implements Filter {      @Override     public void init(FilterConfig filterConfig) throws ServletException {         log.info("初始化过滤器");     }        @Override     public void doFilter(ServletRequest servletRequest, ServletResponse response, FilterChain filterChain) throws IOException, ServletException {         HttpServletRequest request = (HttpServletRequest)servletRequest;         HttpServletResponseWrapper wrapper = new HttpServletResponseWrapper((HttpServletResponse) response);         String requestUri = request.getRequestURI();         log.info("请求地址是:"+requestUri);         if (requestUri.contains("/addSession")             || requestUri.contains("/removeSession")             || requestUri.contains("/online")             || requestUri.contains("/favicon.ico")) {             filterChain.doFilter(servletRequest, response);         } else {             wrapper.sendRedirect("/online");         }     }        @Override     public void destroy() {         //在服务关闭时销毁         log.info("销毁过滤器");     } } 拦截器
  Java中的拦截器是动态拦截 action 调用的对象,然后提供了可以在 action 执行前后增加一些操作,也可以在 action 执行前停止操作,功能与过滤器类似,但是标准和实现方式不同。登录认证:在一些应用中,可能会通过拦截器来验证用户的登录状态,如果没有登录或者登录失败,就会给用户一个友好的提示或者返回登录页面,当然大型项目中都不采用这种方式,都是调单点登录系统接口来验证用户。记录系统日志:我们在常见应用中,通常要记录用户的请求信息,比如请求 ip,方法执行时间等,通过这些记录可以监控系统的状况,以便于对系统进行信息监控、信息统计、计算 PV、性能调优等。通用处理:在应用程序中可能存在所有方法都要返回的信息,这是可以利用拦截器来实现,省去每个方法冗余重复的代码实现。使用拦截器
  我们需要实现 HandlerInterceptor 类,并且重写三个方法:preHandle:在 Controoler 处理请求之前被调用,返回值是 boolean类型,如果是true就进行下一步操作;若返回false,则证明不符合拦截条件,在失败的时候不会包含任何响应,此时需要调用对应的response返回对应响应。postHandler:在 Controoler 处理请求执行完成后、生成视图前执行,可以通过ModelAndView对视图进行处理,当然ModelAndView也可以设置为 null。afterCompletion:在 DispatcherServlet 完全处理请求后被调用,通常用于记录消耗时间,也可以对一些资源进行处理。import lombok.extern.log4j.Log4j2; import org.springframework.stereotype.Component; import org.springframework.web.servlet.HandlerInterceptor; import org.springframework.web.servlet.ModelAndView;  import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpSession;  @Log4j2 @Component public class MyInterceptor implements HandlerInterceptor {     @Override     public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {         log.info("【MyInterceptor】调用了:{}", request.getRequestURI());         request.setAttribute("requestTime", System.currentTimeMillis());         return true;     }      @Override     public void postHandle(HttpServletRequest request, HttpServletResponse response,                            Object handler, ModelAndView modelAndView) throws Exception {         if (!request.getRequestURI().contains("/online")) {             HttpSession session = request.getSession();             String sessionName = (String) session.getAttribute("name");             if ("haixiang".equals(sessionName)) {                 log.info("【MyInterceptor】当前浏览器存在 session:{}",sessionName);             }         }     }      @Override     public void afterCompletion(HttpServletRequest request, HttpServletResponse response,                                 Object handler, Exception ex) throws Exception {         long duration = (System.currentTimeMillis() - (Long)request.getAttribute("requestTime"));         log.info("【MyInterceptor】[{}]调用耗时:{}ms",request.getRequestURI(), duration);     } } 监听器
  监听器通常用于监听 Web 应用程序中对象的创建、销毁等动作的发送,同时对监听的情况作出相应的处理,最常用于统计网站的在线人数、访问量等。关注公众号Java技术栈回复boot可以获取更多系列 Spring Boot 教程。
  监听器大概分为以下几种:ServletContextListener:用来监听 ServletContext 属性的操作,比如新增、修改、删除。HttpSessionListener:用来监听 Web 应用种的 Session 对象,通常用于统计在线情况。ServletRequestListener:用来监听 Request 对象的属性操作。监听器的使用
  我们通过 HttpSessionListener来统计当前在线人数、ip等信息,为了避免并发问题我们使用原子int来计数。
  ServletContext,是一个全局的储存信息的空间,它的生命周期与Servlet容器也就是服务器保持一致,服务器关闭才销毁。
  request,一个用户可有多个;
  session,一个用户一个;而servletContext,所有用户共用一个。所以,为了节省空间,提高效率,ServletContext中,要放必须的、重要的、所有用户需要共享的线程又是安全的一些信息。
  因此我们这里用ServletContext来存储在线人数sessionCount最为合适。
  我们下面来统计当前在线人数:import lombok.extern.log4j.Log4j2;  import javax.servlet.http.HttpSessionEvent; import javax.servlet.http.HttpSessionListener; import java.util.concurrent.atomic.AtomicInteger;  @Log4j2 public class MyHttpSessionListener implements HttpSessionListener {      public static AtomicInteger userCount = new AtomicInteger(0);      @Override     public synchronized void sessionCreated(HttpSessionEvent se) {         userCount.getAndIncrement();         se.getSession().getServletContext().setAttribute("sessionCount", userCount.get());         log.info("【在线人数】人数增加为:{}",userCount.get());                //此处可以在ServletContext域对象中为访问量计数,然后传入过滤器的销毁方法         //在销毁方法中调用数据库入库,因为过滤器生命周期与容器一致     }      @Override     public synchronized void sessionDestroyed(HttpSessionEvent se) {         userCount.getAndDecrement();         se.getSession().getServletContext().setAttribute("sessionCount", userCount.get());         log.info("【在线人数】人数减少为:{}",userCount.get());     } } 过滤器、拦截器、监听器注册实例化三器import com.anqi.tool.sanqi.filter.MyFilter; import com.anqi.tool.sanqi.interceptor.MyInterceptor; import com.anqi.tool.sanqi.listener.MyHttpRequestListener; import com.anqi.tool.sanqi.listener.MyHttpSessionListener; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.boot.web.servlet.ServletListenerRegistrationBean; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.web.servlet.config.annotation.InterceptorRegistry; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;  @Configuration public class WebConfig implements WebMvcConfigurer {     @Autowired     MyInterceptor myInterceptor;      @Override     public void addInterceptors(InterceptorRegistry registry) {         registry.addInterceptor(myInterceptor);     }      /**      * 注册过滤器      * @return      */     @Bean     public FilterRegistrationBean filterRegistrationBean(){         FilterRegistrationBean filterRegistration = new FilterRegistrationBean();         filterRegistration.setFilter(new MyFilter());         filterRegistration.addUrlPatterns("/*");         return filterRegistration;     }      /**      * 注册监听器      * @return      */     @Bean     public ServletListenerRegistrationBean registrationBean(){         ServletListenerRegistrationBean registrationBean = new ServletListenerRegistrationBean();         registrationBean.setListener(new MyHttpRequestListener());         registrationBean.setListener(new MyHttpSessionListener());         return registrationBean;     } } 测试import com.anqi.tool.sanqi.listener.MyHttpSessionListener; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RestController;  import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpSession;  @RestController public class TestController {      @GetMapping("addSession")     public String addSession(HttpServletRequest request) {         HttpSession session = request.getSession();         session.setAttribute("name", "haixiang");         return "当前在线人数" + session.getServletContext().getAttribute("sessionCount") + "人";     }      @GetMapping("removeSession")     public String removeSession(HttpServletRequest request) {         HttpSession session = request.getSession();         session.invalidate();         return "当前在线人数" + session.getServletContext().getAttribute("sessionCount") + "人";     }      @GetMapping("online")     public String online() {         return "当前在线人数" + MyHttpSessionListener.userCount.get() + "人";     }  }
  以下是监听请求的监听器import javax.servlet.ServletRequestEvent; import javax.servlet.ServletRequestListener; import javax.servlet.http.HttpServletRequest;  public class MyHttpRequestListener implements ServletRequestListener {      @Override     public void requestDestroyed(ServletRequestEvent sre) {         System.out.println("request 监听器被销毁");     }      @Override     public void requestInitialized(ServletRequestEvent sre) {         HttpServletRequest req = (HttpServletRequest) sre.getServletRequest();         String requestURI = req.getRequestURI();         System.out.println(requestURI+"--"+"被调用");     } } 拦截器与过滤器的区别
  1.参考标准过滤器是 JavaEE 的标准,依赖于 Servlet 容器,生命周期也与容器一致,利用这一特性可以在销毁时释放资源或者数据入库。拦截器是SpringMVC中的内容,依赖于web框架,通常用于验证用户权限或者记录日志,但是这些功能也可以利用 AOP 来代替。
  2.实现方式过滤器是基于回调函数实现,无法注入 ioc 容器中的 bean。拦截器是基于反射来实现,因此拦截器中可以注入 ioc 容器中的 bean,例如注入 Redis 的业务层来验证用户是否已经登录。

买手机选华为还是小米?(搬运)而对于有性能要求的人来说,就看准备花多少钱,买什么价位的手机了。钱少的百元机,最好还是小米或者红米,尽管做工相对差一点,但是性价比上的优势足以弥补。需要注意的是,百元机里还有挺多老麒麟7nm鸿蒙系统双模5G,售价3699元,网友不等华为P50了华为P50系列已经发布多时,这款原本是上半年发布的高端机,已经推迟到下半年发布了,即便是推迟很长时间发布,仍然无缘5G网络,华为P50系列全系均是4G手机,不仅如此该机发布至今,售英伟达收购案迎来反转,英国终于想清楚了,华为早已做好准备随着半导体技术的不断发展,越来越多的消费者都开始重视到了这项技术。尤其在美国针对华为推出一系列的芯片限制举措以后,对于芯片问题就更加的关注和担心,害怕又一家国产企业像华为一样被断供京东健康,做互联网医疗的探路人我们看见的不仅是一个海角,而是一个新的世界。五百年前,历史学家巴若斯记录了他在抵达好望角时的感受1488年,巴若思乘坐葡萄牙航海家迪亚士率领的船队,从非洲西海岸南亚出发抵达这片海域高并发秒杀系统如何实现正确的扣减库存?作者冰河来源公众号冰河技术不少小伙伴会问扣减商品的库存很简单啊,用户下单的时候扣除对应的商品库存不就行了吗?有那么难吗?确实,理论上就是用户下单后,减去商品的库存就完事了。但是,如峰米R1激光投影怎么样?好不好?值不值得入手?北京时间8月25日,峰米科技在自家的新品发布会上,推出了自家的新款激光电视峰米R1超短焦激光投影仪,峰米一直以来都是小米生态链的一员,早在之前米家就推出过一款激光投影,不过市场上的头条上随便拉黑陌生人是什么行为?心态正常吗?是否属于变态?关于有一些人说一苟不好活!有的人马上就把拉黑!这个人是不正常的!他那个大脑是有一点毛病!不正常的行为!谢谢!自从有了各种社交热点新闻软件,拉黑这种功能也随即上线。拉黑的功能是什么?NokiaG10或将发布,定位游戏智能手机最近有外媒爆料一款名为NokiaG10的手机在马来西亚SIRIM认证局出现了,据悉该机将是G系列的开山之作,定位游戏智能手机。目前诺基亚的品牌为许可人HMDGlobal,该公司近来电脑连不上网?5种方法找原因,轻松解决不犯愁上一期小A和大家分享了电脑的实用技巧与快捷键,这一期我们来讲讲电脑连接不了网络怎么办这一问题。日常使用电脑时网络必不可少,办公娱乐都需要,但由于软件与硬件的不稳定,有时我们会遇到网全球一哥决定删除系统广告,三星这个做法会引发连锁反应吗?大家还记得魅族18系列所宣传的三零系统吗?无推送无广告无预装。当时确实获得了无数网友的点赞,大家也希望其它品牌能跟上。事实上由于魅族的影响力太小,这个做法就是给自己找点营销热点,现谷歌百度们的无人驾驶做到99又如何,最后1定生死越来越多人认识到,自动驾驶征程路漫漫,需要数十年的技术发展和迭代无数资本的投入,才能最终实现所谓的全无人驾驶。在这场慢跑中,胜利属于坚持到最后一刻的人。百度在8月18日召开的百度世
荣耀20以2699元登上战场,其它品牌3000元档手机还能hold得住吗每一次品牌新会发布,就会引来同价位产品一场激烈的竞争,特别是旗舰级产品,总是能获得众人的关注。近日,华为荣耀新系列手机产品发布,作为最受人们关注的荣耀20系列,性价比堪称一流,登上极氪准车主开始转让订单,特斯拉该怪我还是该谢我?7月8日上午,特斯拉中国憋了一波大招国产ModelY标准续航版正式上架,标价27。6万起步(补贴后)。低价的诱惑一度让ModelY出现线上爆单的状况。而ModelY的降价不出意外地曾引领改装新风潮的欧拉好猫,要上GT版了导语俗话说黑猫白猫,能抓耗子就是好猫。于是在欧拉R1和R2相继更名为黑猫和白猫之后,欧拉的第三款喵星人好猫也就应运而生了。或许有人问,可这都是去年的事儿了啊,为什么现在要说欧拉好猫乘联会6月及半年销量榜单公布德系日系微降,自主品牌小幅提升7月9日,乘联会官方公布了2021年6月国内乘用车市场及上半年的最新零售销量数据统计。数据显示,6月份国内狭义乘用车市场销量达157。5万辆,同比下降5。1,环比下降3。116月份财富世界500强榜单出炉,9家中国车企榜上有名8月2日,财富世界500强排行榜发布,今年世界500强排行榜企业的营业收入约为31。7万亿美元,比去年下降5,净利润总和为1。6万亿美元,同比大幅下降20,是2009年以来最大跌幅未来的智能汽车进化过程中的机遇与挑战导语智能汽车作为一种科技消费品,其最核心的特征是可进化。即可通过软硬件的持续迭代更新,以满足消费者不断变化的需求,带来更好的用户体验。在经历了流水化精益化质量管理化信息化和数字化变提车不再等待,第四代飞度5月销量重回8000辆受到芯片和排产影响,今年14月飞度月销量大多在3000至4000辆月,与其去年月平均8000的销量差距较大,有些人开始做文章,认为第四代飞度卖不动了。真是这样么?其实飞度产能目标应让座驾能不断成长的奥秘这台阿凡达发动机可OTA升级导语从前的汽车OTA,仅限于道路救援,远程开锁等情况使用,被称作TBOX。后来的汽车OTA,可升级范围覆盖到车辆的软件系统。现在的汽车OTA,可定向推送和定制升级,覆盖整车所有电器强者并非唯一,别克昂科威Plus意树新Flag在目前国内最主流的中型SUV这一细分市场,久经考验的昂科威系列(累计交付超过100万台)在今年推出Plus版本,以更丰富的科技配置挑战一波市场升级潮。肩负如此重担的昂科威Plus能买不到(买不起)系列丰田全新陆巡GRSport版导语自1951年推出以来,LandCruiser一直被客户选为象征丰田的安全可靠的车辆。已累计销量约1040万台,年销量超过30万台,销往全球170个国家和地区。今年恰逢陆巡推出7马自达的新技术及新产品纷至沓来,ZoomZoom可持续发展宣言2030近日,马自达又发布了展望2030年的新技术及新产品规划。我们可以将这份新技术和新产品规划简单称之为五大方针。先来看看马自达的这份五大方针具体都说了啥?1。活用阶梯式技术发展战略积累