地基代码——自定义注解

import com.didiglobal.ehr.ehrsupport.entity.StaffInfo;
import com.didiglobal.ehr.perfservice.infrastructure.common.annotation.PreventRepeatClick;
import com.didiglobal.ehr.perfservice.infrastructure.common.constant.RedisKeyConstant;
import com.didiglobal.ehr.perfservice.infrastructure.common.exception.BusinessException;
import com.didiglobal.ehr.perfservice.infrastructure.common.exception.MsgCode;
import com.didiglobal.ehr.perfservice.infrastructure.common.util.DateTimeUtil;
import com.didiglobal.ehr.perfservice.infrastructure.common.util.RedisUtil;
import com.didiglobal.ehr.perfservice.infrastructure.common.util.UserInfoHolder;
import com.didiglobal.ehr.perfservice.infrastructure.common.util.ValueUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.reflect.CodeSignature;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;
import java.lang.reflect.Method;
import java.text.MessageFormat;
import java.util.HashMap;
import java.util.Map;


@Component
@Aspect
@Slf4j
public class PreventRepeatClickAspect {

    private static final String ACTION_COUNT_KEY = RedisKeyConstant.OPERATION_LOCK + "{0}-{1}";

    // 防重点击事件类型
    public static final String PREVENT_REPEAT_CLICK_START_CALIBRATE = "PREVENT_REPEAT_CLICK_START_CALIBRATE";

    @Resource
    private RedisUtil redisUtil;

    @Around("@annotation(com.didiglobal.ehr.perfservice.infrastructure.common.annotation.PreventRepeatClick)")
    public Object around(ProceedingJoinPoint joinPoint) throws Throwable {

        MethodSignature signature = (MethodSignature) joinPoint.getSignature();
        Method method = signature.getMethod();
        PreventRepeatClick preventRepeatClick = method.getAnnotation(PreventRepeatClick.class);
        String preventRepeatType = preventRepeatClick.preventRepeatType();
        String uuid = String.valueOf(System.currentTimeMillis());

        if (StringUtils.isBlank(preventRepeatType)) {
            StaffInfo userInfo = UserInfoHolder.getUserInfo();
            if (userInfo == null) {
                log.error("can't get login user");
                return joinPoint.proceed();
            }
            String ldap = userInfo.getLdap();
            String methodName = joinPoint.getSignature().getName();

            String lockKey = MessageFormat.format(ACTION_COUNT_KEY, ldap, methodName);
            // 防重复提交,时间长点,因为主要是用在批量迁移的相关地方,如果执行完成,锁也会单独释放。
            boolean result = redisUtil.lock(lockKey, uuid, 5 * DateTimeUtil.ONE_SECOND_PER_MILL);
            if (!result) {
                throw new BusinessException(MsgCode.COMMON_REPEAT_CLICK);
            }
            try {
                return joinPoint.proceed();
            } finally {
                redisUtil.release(lockKey, uuid);
            }
        } else if (PREVENT_REPEAT_CLICK_START_CALIBRATE.equals(preventRepeatType)) { // 专门给部门开启的时候用
            Map<String, Object> param = new HashMap<>();
            Object[] paramValues = joinPoint.getArgs();
            String[] paramNames = ((CodeSignature) joinPoint.getSignature()).getParameterNames();
            for (int i = 0; i < paramNames.length; i++) {
                param.put(paramNames[i], paramValues[i]);
            }
            Long calibrateUnitId = (Long) param.get("calibrateUnitId");
            if (ValueUtil.nullOrZero(calibrateUnitId)) {
                throw new BusinessException(MsgCode.COMMON_PARAM_ERROR);
            }
            String lockKey = MessageFormat.format(ACTION_COUNT_KEY, PREVENT_REPEAT_CLICK_START_CALIBRATE, calibrateUnitId);

            // 默认设置为3分钟  如果执行完毕 就删除锁
            boolean result = redisUtil.lock(lockKey, uuid, 180 * DateTimeUtil.ONE_SECOND_PER_MILL);
            if (!result) {
                throw new BusinessException(MsgCode.COMMON_REPEAT_CLICK_START_CALIBRATE);
            }
            try {
                return joinPoint.proceed();
            } finally {
                redisUtil.release(lockKey, uuid);
            }
        }
        throw new BusinessException(MsgCode.COMMON_PARAM_ERROR);
    }
}
// 注解类
import java.lang.annotation.*;

@Target({ElementType.METHOD, ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface PreventRepeatClick {

    String preventRepeatType() default "";

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值