【AOP】自定义注解 + 拦截器 + 配置类实现AOP

场景介绍

对标注了特定的自定义注解方法,在进入方法前会进行一些操作来获取特定的参数,这些参数可以放进上下文中,在业务逻辑代码中可以从上下文直接获取。

案例一:实现HandlerInterceptor

@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface InjectAppId {
}
public class AppIdInjectInterceptor2 implements HandlerInterceptor {
    public static Logger LOGGER = TrussLoggerFactory.getLogger(AppIdInjectInterceptor2.class);

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
        throws Exception {
        LOGGER.info("AppIdInjectInterceptor is start");
        HandlerMethod handlerMethod = (HandlerMethod) handler;
        InjectAppId injectAppId = handlerMethod.getMethod().getAnnotation(InjectAppId.class);
        if (injectAppId == null) {
            // 直接通过
            return true;
        }

        // 有InjectAppId注解,将AppId注入上下文后通过
        Optional<AccountInfoBean> accountInfoBean = JwtUtils.getAccountInfoBean(request.getHeader("authorization"));
        if (!accountInfoBean.isPresent()) {
            LOGGER.error("JwtUtils parsing token failure.");
            throw new CommonStorageException(CommonErrorCode.JWTUTILS_ANALYSIS_TOKEN_ERROR);
        }
        String appId = accountInfoBean.get().getProject();
        LOGGER.info("AppId is :{}", appId);
        IRequestContext requestContext = RequestContext.getCurrent();
        requestContext.setItem("appId", appId);

        return true;
    }
}
@Configuration
public class MyInterceptorConfigurer implements WebMvcConfigurer {
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new AppIdInjectInterceptor2());
    }
}

案例二:实现MethodInterceptor(配置类)

@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface InjectAppId {
}
@Named
public class AppIdInjectInterceptor implements MethodInterceptor {
    public static Logger LOGGER = TrussLoggerFactory.getLogger(AppIdInjectInterceptor.class);

    @Override
    public Object invoke(MethodInvocation invocation) throws Throwable {
        LOGGER.info("AppIdInjectInterceptor is start");
        InjectAppId injectAppId = this.getInjectAppId(invocation);
        if (injectAppId == null) {
            return invocation.proceed();
        }
        LOGGER.info("The current method annotation is {}:", injectAppId);

        doInjectAppId();
        return invocation.proceed();
    }

    /**
     * 往上下文注入AppId
     */
    private void doInjectAppId() throws CommonStorageException {
        LOGGER.info("doInjectAppId is start");

        // 获取AppId
        ServletRequestAttributes requestAttributes =
            (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
        if (requestAttributes == null) {
            LOGGER.error("Get httpRequest failure.");
            throw new CommonStorageException(CommonErrorCode.HTTP_REQUEST_ERROR);
        }
        HttpServletRequest request = requestAttributes.getRequest();
        Optional<AccountInfoBean> accountInfoBean = JwtUtils.getAccountInfoBean(request.getHeader("authorization"));
        if (!accountInfoBean.isPresent()) {
            LOGGER.error("JwtUtils parsing token failure.");
            throw new CommonStorageException(CommonErrorCode.JWTUTILS_ANALYSIS_TOKEN_ERROR);
        }
        String appId = accountInfoBean.get().getProject();
        LOGGER.info("AppId is :{}", appId);

        // 放入上下文中
        IRequestContext requestContext = RequestContext.getCurrent();
        requestContext.setItem("appId", appId);
    }

    /**
     * 获取InjectAppId注解类
     *
     * @param invocation invocation
     * @return InjectAppId
     */
    private InjectAppId getInjectAppId(MethodInvocation invocation) {
        Method method = invocation.getMethod();
        method = ClassUtils.getMostSpecificMethod(method, invocation.getThis().getClass());
        return method.getAnnotation(InjectAppId.class);
    }
}
@Configuration
public class InterceptorConfig {
    public static final String traceAnnotationExecution =
        "@annotation(com.hihonor.it.hcc.storage.common.annotation.InjectAppId)";

    @Bean
    public DefaultPointcutAdvisor appIdPointcutAdvisor() {
        AppIdInjectInterceptor appIdInjectInterceptor = new AppIdInjectInterceptor();
        DefaultPointcutAdvisor advisor = new DefaultPointcutAdvisor();
        AspectJExpressionPointcut pointcut = new AspectJExpressionPointcut();
        pointcut.setExpression(traceAnnotationExecution);
        advisor.setPointcut(pointcut);
        advisor.setAdvice(appIdInjectInterceptor);

        return advisor;
    }
}

案例三:实现MethodInterceptor(applicationContext.xml文件)

@Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface InjectAppId {
}
@Named
public class AppIdInjectInterceptor implements MethodInterceptor {
    public static Logger LOGGER = TrussLoggerFactory.getLogger(AppIdInjectInterceptor.class);

    @Override
    public Object invoke(MethodInvocation invocation) throws Throwable {
        LOGGER.info("AppIdInjectInterceptor is start");
        InjectAppId injectAppId = this.getInjectAppId(invocation);
        if (injectAppId == null) {
            return invocation.proceed();
        }
        LOGGER.info("The current method annotation is {}:", injectAppId);

        doInjectAppId();
        return invocation.proceed();
    }

    /**
     * 往上下文注入租户AppId
     */
    private void doInjectAppId() throws CommonStorageException {
        LOGGER.info("doInjectAppId is start");

        // 获取AppId
        ServletRequestAttributes requestAttributes =
            (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
        if (requestAttributes == null) {
            LOGGER.error("Get httpRequest failure.");
            throw new CommonStorageException(CommonErrorCode.HTTP_REQUEST_ERROR);
        }
        HttpServletRequest request = requestAttributes.getRequest();
        Optional<AccountInfoBean> accountInfoBean = JwtUtils.getAccountInfoBean(request.getHeader("authorization"));
        if (!accountInfoBean.isPresent()) {
            LOGGER.error("JwtUtils parsing token failure.");
            throw new CommonStorageException(CommonErrorCode.JWTUTILS_ANALYSIS_TOKEN_ERROR);
        }
        String appId = accountInfoBean.get().getProject();
        LOGGER.info("AppId is :{}", appId);

        // 放入上下文中
        IRequestContext requestContext = RequestContext.getCurrent();
        requestContext.setItem("appId", appId);
    }

    /**
     * 获取InjectAppId注解类
     *
     * @param invocation invocation
     * @return InjectAppId
     */
    private InjectAppId getInjectAppId(MethodInvocation invocation) {
        Method method = invocation.getMethod();
        method = ClassUtils.getMostSpecificMethod(method, invocation.getThis().getClass());
        return method.getAnnotation(InjectAppId.class);
    }
}

applicationContext.xml文件

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans
  http://www.springframework.org/schema/beans/spring-beans-3.1.xsd
  http://www.springframework.org/schema/aop 
  http://www.springframework.org/schema/aop/spring-aop-3.1.xsd" default-lazy-init="true">
       
    <beans>
        <aop:config>
            <aop:advisor advice-ref="programItemsInjectInterceptor" order="60"
                pointcut="(execution(@com.nxq.it.common.annotation.InjectProgramItems * com.nxq..*Service.*(..))) or (execution(@com.nxq.it.common.annotation.InjectProgramItems * com.nxq..*Servlet.*(..)))"/>
        </aop:config>
    </beans>
</beans>
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值