详解HandlerInterceptor接口(记录)

  • HandlerInterceptor接口是Spring框架中用于拦截HTTP请求的接口,它提供了三个方法,分别在请求处理之前、请求处理之后和请求处理完成之后被调用。

实现HandlerInterceptor接口可以帮助我们拦截HTTP请求,并在请求处理之前、之后、以及完成之后执行自定义的逻辑。

public interface HandlerInterceptor {
    default boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        return true;
    }

    default void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable ModelAndView modelAndView) throws Exception {
    }

    default void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable Exception ex) throws Exception {
    }
}
    

通常情况下,我们可以使用HandlerInterceptor来实现以下功能:

  • 身份认证:在请求处理之前,我们可以使用HandlerInterceptor来检查用户是否已经通过身份认证。如果未通过身份认证,则可以将请求重定向到登录页面或返回错误信息。
@Component
public class AuthInterceptor implements HandlerInterceptor {
   @Override
   public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
       //检查是否认证
       if (!isAuthenticated(request)) {
           response.sendRedirect("/login");
           return false;
       }
       return true;
   }

   private boolean isAuthenticated(HttpServletRequest request) {
       //检查用户是否认证
       // 如果经过身份验证,则返回true,否则返回false
   }
}
  • 日志记录:在请求处理之前和之后,我们可以使用HandlerInterceptor来记录请求的详细信息,例如请求URL、请求参数、响应状态码等。
@Component
public class LoggingInterceptor implements HandlerInterceptor {
    private static final Logger LOGGER = LoggerFactory.getLogger(LoggingInterceptor.class);
 /**
  * LoggerFactory.getLogger(LoggingInterceptor.class)是用于创建日志记录器(Logger)的方法,它是由Slf4j日志框架提供的。
  * 在这个例子中,我们使用LoggerFactory.getLogger(LoggingInterceptor.class)方法创建一个名为LoggingInterceptor的日志记录器。
  * 日志记录器(Logger)是用于记录应用程序运行时信息的对象。它们通常用于记录调试信息、错误信息、性能信息等。
  * Slf4j是一个广泛使用的Java日志框架,它提供了一种简单的方式来记录日志,并且可以与多个日志实现(例如Logback、Log4j、Java Util Logging等)进行集成。
  */

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        LOGGER.info("收到请求: {} {}", request.getMethod(), request.getRequestURI());
        return true;
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        LOGGER.info("已发送响应: {}", response.getStatus());
    }
}
实现了一个LoggingInterceptor类,用于记录HTTP请求和响应的详细信息。
在preHandle方法中,我们记录请求的HTTP方法和请求URL。
在afterCompletion方法中,我们记录响应的状态码。
  • 性能监控:在请求处理之前和之后,我们可以使用HandlerInterceptor来记录请求的处理时间,以便监控应用程序的性能。
@Component
public class PerformanceInterceptor implements HandlerInterceptor {
    private static final Logger LOGGER = LoggerFactory.getLogger(PerformanceInterceptor.class);
    private static final ThreadLocal<Long> START_TIME = new ThreadLocal<>();
/**
 *定义了一个名为START_TIME的ThreadLocal变量,用于在多线程环境下记录请求处理的开始时间。
 ThreadLocal是一个Java类,它可以为每个线程存储一个独立的变量副本。
 因此,每个线程都可以独立地访问和修改该变量的值,而不会影响其他线程。在多线程环境下,使用ThreadLocal可以避免线程安全问题,从而提高程序的并发性能。
 */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        START_TIME.set(System.currentTimeMillis());
        return true;
    }

    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        long duration = System.currentTimeMillis() - START_TIME.get();
        LOGGER.info("请求消耗 {} ms: {} {}", duration, request.getMethod(), request.getRequestURI());
    }
}

注意,由于ThreadLocal变量是与线程相关的,因在使用完毕后,显式地调用ThreadLocalremove()方法,以避免内存泄漏。
这个例子中,没有显式地调用remove()方法,因为该变量是静态的,且不会随着线程的结束而被销毁。
  • 请求重定向:在请求处理之前或之后,我们可以使用HandlerInterceptor来将请求重定向到其他URL,例如重定向到错误页面或其他应用程序。
@Component
public class RedirectInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        //如果需要重定向,则返回true,否则返回false
        if (shouldRedirect(request)) {
            response.sendRedirect("/new-url");
            return false;
        }
        return true;
    }

    private boolean shouldRedirect(HttpServletRequest request) {
        // 检查是否需要重定向请求
        // 如果需要重定向,则返回true,否则返回false
    }
}
  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值