问题描述
在拦截器拦截登录请求,想通过从redis中取出token,判断token是否为null,进而判断是否登录。
@Component
public class LoginInterceptor implements HandlerInterceptor {
@Autowired
StringRedisTemplate redisTemplate;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
String token = request.getHeader("token");
ValueOperations<String, String> valueOperations = redisTemplate.opsForValue();
String s = valueOperations.get(token);
if (Strings.isNotEmpty(s)) {
JSONObject jsonObject = JSON.parseObject(s);
if (jsonObject != null) {
return true;
}
}
throw new NotLoginException("用户未登录");//使用异常捕获,可以为前端返回自定义的信息
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {}
}
执行代码,发现空指针异常,debug后发现空指针出现在redisTemplate.opsForValue()
错误原因
在拦截器配置类中,我们使用**new LoginInterceptor()**将自定义创建的拦截器加入到拦截器中
@Configuration
public class InterceptorConfig implements WebMvcConfigurer {
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(new LoginInterceptor());
}
}
此时就出现了问题,我们使用的是自己new出来的LoginInterceptor,在LoginInterceptor中我使用@autowired自动装配StringRedisTemplate()。而自动装配必须彼此都是ioc容器中的实例。不能使用我自己new 出来的 LoginInterceptor。
所以在LoginInterceptor中自动装配StringRedisTemplate失败
改正
将配置类改为
@Configuration
public class InterceptorConfig implements WebMvcConfigurer {
@Autowired
LoginInterceptor loginInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(loginInterceptor);
}
}
此时,我们使用的就是ioc中的LoginInterceptor了,问题解决。