zoukankan      html  css  js  c++  java
  • 自定义参数转换器

    方法参数转换器

    HandlerMethodArgumentResolver

    介绍

    使用方法参数转化器[HandlerMethodArgumentResolver]给controller的自定义参数赋值.

    使用场景

    例:从请求头获取用户信息
    现在的方案:获取"SCRM-BASICS"请求头中的数据,然后转换后再获取企业id,自己手动转换,我们可以使用方法参数转换器,自动封装到一个参数中.

    @PostMapping("/friends/create")
    @ApiOperation(value = "好友助力-创建好友助力活动", notes = "创建好友助力活动")
    public BaseResult createFriends(
            @RequestHeader("SCRM-BASICS") String scrm,
            @Valid @RequestBody CreateFriendsReqVO req) throws FriendsHelpException {
        log.info("好友助力-创建好友助力活动请求头信息,userInfo:{},入参:{}", scrm, JSONUtil.toJsonStr(req));
        if (StringUtils.isEmpty(scrm)) {
            throw new FriendsHelpException(NO_LOGIN_ERROR);
        }
        return  helpService.createFriends(new ScrmBasics(scrm).getCorpId(), new ScrmBasics(scrm).getAccountId(), req);
    }
    
    

    替代方案

    使用HandlerMethodArgumentResolver

    @ApiOperation("新增菜单")
    @PostMapping("/add")
    public R addMenu(
            @ApiIgnore @CurrentUser CU cu,//我们需要用代码实现,把用户id,自动注入到添加了@CurrentUser注解的CU 类型的cu中
            @Validated(value = {BaseInsert.class}) @RequestBody MenuReqVO req
    ) {
        log.info("新增菜单,参数:{}", JSONUtil.toJsonStr(req));
        return menuService.add(cu, req);
    }
    
    

    实现步骤

    创建一个实体

    创建一个实体,用于接收数据

    @Data
    @AllArgsConstructor
    public class CU {
    
        /**
         * 用户id
         */
        private Long userId;
    }
    
    
    
    

    创建一个注解

    创建一个注解用于精确定位

    @Target({ElementType.PARAMETER})
    @Retention(RetentionPolicy.RUNTIME)
    @Documented
    public @interface CurrentUser {
    
    }
    
    

    创建一个转换器

    /**
     *该类会在controller的每个方法执行前调用,执行supportsParameter()判断是否转换,调用resolveArgument()转换参数
     */
    @Component
    @Slf4j
    public class CurrentUserResolver implements HandlerMethodArgumentResolver {
    
        //判断是否进行转化
        @Override
        public boolean supportsParameter(MethodParameter parameter) {
            //判断这个方法参数列表中是否具有CU这个类,是否有CurrentUser这个注解
            return parameter.getParameterType().isAssignableFrom(CU.class)
                    && parameter.hasParameterAnnotation(CurrentUser.class);
        }
    
    
        //具体转换逻辑
        @Override
        public Object resolveArgument(MethodParameter methodParameter, ModelAndViewContainer modelAndViewContainer, NativeWebRequest nativeWebRequest, WebDataBinderFactory webDataBinderFactory) {
            //获取请求头的信息,解析出请求信息
            String accessToken = nativeWebRequest.getHeader("accessToken");
            try {
                Claims claims = JwtUtil.parseJWT(accessToken);
                String subject = claims.getSubject();
                LoginUserInfo info = JSONUtil.toBean(subject, LoginUserInfo.class);
                Long userId = info.getUserId();
                //返回要注入的对象            
                return new CU(userId);
            } catch (Exception e) {
                log.warn("token解析异常");
            }
            return null;
        }
    }
    
    

    把转换器注册到spring中

    @Configuration
    public class CorsConfig implements WebMvcConfigurer {
    
        @Autowired
        private CurrentUserResolver currentUserResolver;
    
        @Override
        public void addArgumentResolvers(List<HandlerMethodArgumentResolver> resolvers) {
            resolvers.add(currentUserResolver);
        }
    }
    
    
  • 相关阅读:
    WPF 自定义NotifyPropertyChanged
    深度学习(五)正则化之L1和L2
    深度学习(三) 反向传播直观理解
    javascript中的原型和原型链(二)
    javascript中的原型和原型链(一)
    javascript中创建对象的方式及优缺点(二)
    javascript中创建对象的方式及优缺点(一)
    JS实现深拷贝的几种方法
    json.stringify()的妙用,json.stringify()与json.parse()的区别
    Javascript你必须要知道的知识点
  • 原文地址:https://www.cnblogs.com/songfahzun/p/15745496.html
Copyright © 2011-2022 走看看