Spring MVC 拦截器

应用场景

在接口请求之前,想对请求做一些特定的操作例如校验是否存在token、token是否合规以及禁用某些路径时可以使用拦截器。

WebMvcConfigurer实现拦截器

首先定义一个注册类

实现HandlerInterceptor并重写其中的方法来自定义对请求的各种操作。

其中包含三种方法

1.perHandle: 在请求controller之前进行操作,按声明顺序执行,如果返回false则中断执行。

2.postHandle: 前置条件:perHandle返回true。在controller方法处理完之后DispatcherServlet进行视图渲染之前执行,在该方法中可对ModelAndView进行操作。

3.afterCompletion:前置条件:preHandle返回true。在视图渲染之后执行,多用于清理资源。

 

@Component
@Slf4j
public class SwaggerInterceptor implements HandlerInterceptor {

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        log.info("在请求controller前进行了拦截:preHandle");
        // 阻止对 Swagger 路径的访问,并返回 403 Forbidden 错误
        response.sendError(HttpServletResponse.SC_FORBIDDEN, "Access to Swagger UI is disabled.");
        return false;  // 返回 false,阻止请求继续处理
    }
}

再定义拦截器

使用注解@Configuration声明一个配置类,实现WebMvcConfigurer方法。

重写其中的addInterceptors方法,在其中的addPathPatterns来自定义拦截某些路径。

@Configuration
public class WebConfig implements WebMvcConfigurer {

    @Resource
    private SwaggerInterceptor swaggerInterceptor;

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        InterceptorRegistration interceptorRegistration = registry.addInterceptor(swaggerInterceptor);
        interceptorRegistration.addPathPatterns("/**");
    }
}

但该拦截器会和Spring Boot的自动配置机制出现冲突,导致拦截器不生效的情况。

因为 Spring Boot通过@EnableAutoConfiguration注解自动配置Spring MVC的默认设置。当你使用WebMvcConfigurer接口时,它是为了让你在不禁用Spring Boot的自动配置的情况下对Spring MVC进行定制和扩展。Spring Boot会自动检测实现了WebMvcConfigurer接口的类,并将其用于MVC的自定义配置。

  • WebMvcConfigurer:是一个接口,允许你在保留Spring Boot自动配置的前提下,提供自己的MVC配置。你可以使用它来添加拦截器、格式化器等,而不破坏Spring Boot的自动配置。

解决该类问题则需要另一种方式来写拦截器

WebMvcConfigurationSupport实现拦截器

首先引入依赖包

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-security</artifactId>
        </dependency>

其中注册类不变,只是定义的拦截器要继承WebMvcConfigurationSupport。

@Configuration
public class WebConfig extends WebMvcConfigurationSupport {

    @Resource
    private SwaggerInterceptor swaggerInterceptor;

    @Override
    public void addInterceptors(InterceptorRegistry registry) {

        InterceptorRegistration interceptorRegistration = registry.addInterceptor(swaggerInterceptor);
        interceptorRegistration.addPathPatterns("/**");
    }
}
  • WebMvcConfigurationSupport:是一个配置基类,提供了Spring MVC的完整配置能力。当你继承它时,Spring Boot的自动配置将被完全禁用,你需要自己提供所有的配置细节。
  • 当你继承WebMvcConfigurationSupport时,你接管了整个Spring MVC配置,因此你完全掌控了拦截器的注册和使用。这种方式虽然灵活,但会禁用Spring Boot的所有自动配置(例如视图解析器、消息转换器等),这可能会导致你需要手动配置很多额外的内容

但是引入了security会为应用提供一些内置的默认行为,例如登录、注销(/login  /logout)

如若请求失败则会进行重定向进而暴露服务器的IP端口。

解决该类问题有两种方法

1.禁用 /logout路径

@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .logout().disable() // 禁用默认的/logout行为
            .authorizeRequests()
            .anyRequest().authenticated()  // 所有请求需要认证
            .and()
            .formLogin();  // 启用表单登录
    }
}

2.自定义/logout行为

@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .logout()
            .logoutUrl("/custom-logout")  // 自定义注销路径
            .logoutSuccessUrl("/login?logout")  // 注销成功后重定向到指定页面
            .invalidateHttpSession(true)  // 注销时使会话无效
            .deleteCookies("JSESSIONID")  // 注销时删除指定的cookie
            .and()
            .authorizeRequests()
            .anyRequest().authenticated()
            .and()
            .formLogin();
    }
}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值