通过aop、el表达式获取入参或者修改,管理不同用户的权限

先贴两个工具类:
public class ExpressionRootObject {
    private final Object object;
    private final Object[] args;

    public ExpressionRootObject(Object object, Object[] args) {
        this.object = object;
        this.args = args;
    }

    public Object getObject() {
        return object;
    }

    public Object[] getArgs() {
        return args;
    }
}

import org.springframework.aop.support.AopUtils;
import org.springframework.context.expression.AnnotatedElementKey;
import org.springframework.context.expression.CachedExpressionEvaluator;
import org.springframework.context.expression.MethodBasedEvaluationContext;
import org.springframework.core.DefaultParameterNameDiscoverer;
import org.springframework.core.ParameterNameDiscoverer;
import org.springframework.expression.EvaluationContext;
import org.springframework.expression.Expression;

import java.lang.reflect.Method;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;


public class ExpressionEvaluator<T> extends CachedExpressionEvaluator {
    private final ParameterNameDiscoverer paramNameDiscoverer = new DefaultParameterNameDiscoverer();
    private final Map<ExpressionKey, Expression> conditionCache = new ConcurrentHashMap<>(64);
    private final Map<AnnotatedElementKey, Method> targetMethodCache = new ConcurrentHashMap<>(64);


    public EvaluationContext createEvaluationContext(Object object, Class<?> targetClass, Method method, Object[] args) {
        Method targetMethod = getTargetMethod(targetClass, method);
        ExpressionRootObject root = new ExpressionRootObject(object, args);
        return new MethodBasedEvaluationContext(root, targetMethod, args, this.paramNameDiscoverer);
    }


    public T getValue(String conditionExpression, AnnotatedElementKey elementKey, EvaluationContext evalContext, Class<T> clazz) {
        return getExpression(this.conditionCache, elementKey, conditionExpression).getValue(evalContext, clazz);
    }

    public void setValue(String conditionExpression, AnnotatedElementKey elementKey, EvaluationContext evalContext, Object value) {
         getExpression(this.conditionCache, elementKey, conditionExpression).setValue(evalContext, value);
    }

    private Method getTargetMethod(Class<?> targetClass, Method method) {
        AnnotatedElementKey methodKey = new AnnotatedElementKey(method, targetClass);
        Method targetMethod = this.targetMethodCache.get(methodKey);
        if (targetMethod == null) {
            targetMethod = AopUtils.getMostSpecificMethod(method, targetClass);
            if (targetMethod == null) {
                targetMethod = method;
            }
            this.targetMethodCache.put(methodKey, targetMethod);
        }
        return targetMethod;
    }
}

一个aop基础类:

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.context.expression.AnnotatedElementKey;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.expression.EvaluationContext;

import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import java.lang.reflect.ParameterizedType;
import java.util.Arrays;
import java.util.List;

/**
 * 类 描 述:资源切片的基础类
 * 创建时间:2021/12/21 上午9:30
 * 创 建 :gzc
 */
public class BaseResourceAspect<T extends Annotation> {

    private ExpressionEvaluator<String> evaluator = new ExpressionEvaluator<>();

    //只获取方法上的注解信息  没有获取类上的信息
    /*public T getAnnotion(JoinPoint joinPoint){
        MethodSignature signature = (MethodSignature) joinPoint.getSignature();
        Method method = signature.getMethod();
        Class<T> actualTypeArgument = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
        return  method.getAnnotation(actualTypeArgument);
    }*/

    public T getAnnotion(JoinPoint pj) {
        // 获取切入的 Method
        MethodSignature joinPointObject = (MethodSignature) pj.getSignature();
        Method method = joinPointObject.getMethod();
        Class<T> actualTypeArgument = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];

        boolean flag = method.isAnnotationPresent(actualTypeArgument);
        if (flag) {
            T annotation = method.getAnnotation(actualTypeArgument);
            return annotation;
        } else {
            // 如果方法上没有注解,则搜索类上是否有注解
            T classAnnotation = AnnotationUtils.findAnnotation(joinPointObject.getMethod().getDeclaringClass(), actualTypeArgument);
            if (classAnnotation != null) {
                return classAnnotation;
            } else {
                return null;
            }
        }
    }


    /**
     * el 取值
     * @param joinPoint
     * @return
     */
    public String getValue(JoinPoint joinPoint,String el) {
        if (joinPoint.getArgs() == null) {
            return null;
        }
        EvaluationContext evaluationContext = evaluator.createEvaluationContext(joinPoint.getTarget(), joinPoint.getTarget().getClass(), ((MethodSignature) joinPoint.getSignature()).getMethod(), joinPoint.getArgs());
        AnnotatedElementKey methodKey = new AnnotatedElementKey(((MethodSignature) joinPoint.getSignature()).getMethod(), joinPoint.getTarget().getClass());
        return evaluator.getValue(el, methodKey, evaluationContext, String.class);
    }

    /**
     * el 设置值
     * @param joinPoint
     * @param value
     */
    public Object[] setValue(JoinPoint joinPoint,String el,Object value) {
        Object[] args = joinPoint.getArgs();
        List<String> argNames = Arrays.asList(((MethodSignature) joinPoint.getSignature()).getParameterNames());
        String arg = el.replace("#", "").split("\\.")[0];
        int index = argNames.indexOf(arg);
        if (index < 0){
            return args;
        }
        if (!isPrimite(((MethodSignature) joinPoint.getSignature()).getParameterTypes()[index])) {
            EvaluationContext evaluationContext = evaluator.createEvaluationContext(joinPoint.getTarget(), joinPoint.getTarget().getClass(), ((MethodSignature) joinPoint.getSignature()).getMethod(), joinPoint.getArgs());
            AnnotatedElementKey methodKey = new AnnotatedElementKey(((MethodSignature) joinPoint.getSignature()).getMethod(), joinPoint.getTarget().getClass());
            evaluator.setValue(el, methodKey, evaluationContext, value);
        }else{
            args[index] = value;
        }
        return args;
    }

    /**
     * 判断是否是基本类型
     * @param clazz
     * @return
     */
    private boolean isPrimite(Class clazz) {
        if (clazz.isPrimitive() || clazz == String.class
                || clazz == Byte.class || clazz == Short.class
                || clazz == Integer.class || clazz == Long.class
                || clazz == Float.class || clazz == Double.class
                || clazz == Boolean.class || clazz == Character.class) {
            return true;
        } else {
            return false;
        }
    }
}

例子:

@Target({ElementType.METHOD,ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Inherited
@Documented
public @interface ListLimit {
    //设置PageNo的el表达式
    String pageNoEl() default "";
    //设置PageSize的el表达式
    String pageSizeEl() default "";

    boolean check() default true;
    //商品库
    FunctionEnum type() default FunctionEnum.ITEM_LIST;
}
@Component
@Aspect
@Slf4j
public class ListLimitAspect extends BaseResourceAspect<ListLimit> {

    @Resource
    IResourceFacade resourceFacade;

    @Pointcut("@annotation(com.taosj.industry.common.annotation.ur.ListLimit) || @within(com.taosj.industry.common.annotation.ur.ListLimit)")
    private void pointcut() {

    }

    @Around(value = "pointcut()")
    public Object doAround(JoinPoint joinPoint) throws Throwable {
        ListLimit handler = getAnnotion(joinPoint);
        Object[] args = new Object[0];
        if(handler.check()){
            FunctionPo function = resourceFacade.getFunctionByEnum(handler.type());
            if (FunctionValueTypeEnum.INT.getName().equals(function.getFuncValueType())){
                try {
                    args =  setValue(joinPoint,handler.pageNoEl(),1);
                    args =  setValue(joinPoint,handler.pageSizeEl(),Integer.parseInt(function.getFuncValue()));
                }catch (Exception e) {
                    log.error("ListLimitAspect:setValue error value:{};top:{}",handler.pageSizeEl(),function.getFuncValue());
                }
            }
        }
        Object obj = args != null && args.length != 0 ? ((ProceedingJoinPoint)joinPoint).proceed(args) : ((ProceedingJoinPoint)joinPoint).proceed();
      //  Object obj = ((ProceedingJoinPoint)joinPoint).proceed();
        return obj;
    }


}

使用例子 在方法头上加:

@ListLimit(pageNoEl = "#pageNo",pageSizeEl = "#pageSize")
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值