当前位置: 首页>前端>正文

springboot 响应拦截添加响应头 springboot拦截器添加参数

传统拦截器的写法

第一步创建一个类实现HandlerInterceptor接口,重写接口的方法。

springboot 响应拦截添加响应头 springboot拦截器添加参数,springboot 响应拦截添加响应头 springboot拦截器添加参数_自定义拦截器,第1张

第二步在XML中进行如下配置,就可以实现自定义拦截器了

springboot 响应拦截添加响应头 springboot拦截器添加参数,springboot 响应拦截添加响应头 springboot拦截器添加参数_拦截器_02,第2张

SpringBoot实现自定义拦截器方法

实现自定义拦截器只需要3步:
1、创建我们自己的拦截器类并实现 HandlerInterceptor 接口。
2、创建一个Java类继承WebMvcConfigurerAdapter,并重写 addInterceptors 方法。
3、实例化我们自定义的拦截器,然后将对像手动添加到拦截器链中(在addInterceptors方法中添加)。

第一步创建一个类实现HandlerInterceptor接口,重写接口的方法,只是多了一个@Component注解,这个注解是为后面的使用时进行注入。例:

springboot 响应拦截添加响应头 springboot拦截器添加参数,springboot 响应拦截添加响应头 springboot拦截器添加参数_拦截器_03,第3张

第二步在入口类的目录或者兄弟目录下创建一个类继承WebMvcConfigurerAdapter类并重写addInterceptors方法;

@SpringBootConfiguration注解表明这是一个配置类

springboot 响应拦截添加响应头 springboot拦截器添加参数,springboot 响应拦截添加响应头 springboot拦截器添加参数_自定义拦截器_04,第4张

到这里已经实现了自定义拦截器。SpringBoot实现自定义拦截器跟传统不一样的地方只是将XML配置变更为JAVA配置而已。

自定义权限注解

定义一个@interface类
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Access {
 
    String[] value() default {};
 
    String[] authorities() default {};
 
    String[] roles() default {};
 
}

@Target注解是标注这个类它可以标注的位置:
常用的元素类型(ElementType):

public enum ElementType {
    /** Class, interface (including annotation type), or enum declaration */
    // TYPE类型可以声明在类上或枚举上或者是注解上
    TYPE,
    /** Field declaration (includes enum constants) */
    // FIELD声明在字段上
    FIELD,
    /** Method declaration */
    // 声明在方法上
    METHOD,
    /** Formal parameter declaration */
    // 声明在形参列表中
    PARAMETER,
    /** Constructor declaration */
    // 声明在构造方法上
    CONSTRUCTOR,
    /** Local variable declaration */
    // 声明在局部变量上
    LOCAL_VARIABLE,
    /** Annotation type declaration */
    ANNOTATION_TYPE,
    /** Package declaration */
    PACKAGE,
    /**
     * Type parameter declaration
     *
     * @since 1.8
     */
    TYPE_PARAMETER,
    /**
     * Use of a type
     *
     * @since 1.8
     */
    TYPE_USE
}

@Retention注解表示的是本注解(标注这个注解的注解保留时期)

public enum RetentionPolicy {
    /**
     * Annotations are to be discarded by the compiler.
     */
    // 源代码时期
    SOURCE,
    /**
     * Annotations are to be recorded in the class file by the compiler
     * but need not be retained by the VM at run time.  This is the default
     * behavior.
     */
    // 字节码时期, 编译之后
    CLASS,
    /**
     * Annotations are to be recorded in the class file by the compiler and
     * retained by the VM at run time, so they may be read reflectively.
     *
     * @see java.lang.reflect.AnnotatedElement
     */
     // 运行时期, 也就是一直保留, 通常也都用这个
    RUNTIME
}

@Documented是否生成文档的标注, 也就是生成接口文档是, 是否生成注解文档
注解说完了, 下面需要到对应的controller的方法中取添加注解, 配置该方法允许的权限

在方法上配置权限
@RestController
public class HelloController {
 
    @RequestMapping(value = "/admin", produces = MediaType.APPLICATION_JSON_UTF8_VALUE, method = RequestMethod.GET)
    // 配置注解权限, 允许身份为admin, 或者说允许权限为admin的人访问
    @Access(authorities = {"admin"})
    public String hello() {
        return "Hello, admin";
    }
}
编写权限拦截逻辑
// 自定义一个权限拦截器, 继承HandlerInterceptorAdapter类
public class AuthenticationInterceptor extends HandlerInterceptorAdapter {
 
    // 在调用方法之前执行拦截
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        // 将handler强转为HandlerMethod, 前面已经证实这个handler就是HandlerMethod
        HandlerMethod handlerMethod = (HandlerMethod) handler;
        // 从方法处理器中获取出要调用的方法
        Method method = handlerMethod.getMethod();
        // 获取出方法上的Access注解
        Access access = method.getAnnotation(Access.class);
        if (access == null) {
        // 如果注解为null, 说明不需要拦截, 直接放过
            return true;
        }
        if (access.authorities().length > 0) {
            // 如果权限配置不为空, 则取出配置值
            String[] authorities = access.authorities();
            Set<String> authSet = new HashSet<>();
            for (String authority : authorities) {
            // 将权限加入一个set集合中
                authSet.add(authority);
            }
            // 这里我为了方便是直接参数传入权限, 在实际操作中应该是从参数中获取用户Id
            // 到数据库权限表中查询用户拥有的权限集合, 与set集合中的权限进行对比完成权限校验
            String role = request.getParameter("role");
            if (StringUtils.isNotBlank(role)) {
                if (authSet.contains(role)) {
                // 校验通过返回true, 否则拦截请求
                    return true;
                }
            }
        }
        // 拦截之后应该返回公共结果, 这里没做处理
        return false;
    }
 
}



https://www.xamrdz.com/web/2a21964439.html

相关文章: