赞
踩
首先自定义参数注解,然后根据AOP思想,找到该注解作用的切点,也就是mapper层对于mapper层的接口在执行前都会执行该aop操作:获取到对于的方法对象,根据方法对象获取参数列表,根据参数列表判断某个参数上是否加有自定义的注解,如果有则读取注解中的value值,并通过传入对象的引用拿到该对象,此时判断该对象的id值是否位空,如果为空则生成全局唯一id并赋值
- package com.cloud.cloud_oj_learn.aspects;
-
- import com.cloud.cloud_oj_common.annotations.GenerateId;
- import com.cloud.cloud_oj_common.enums.Keys;
- import jakarta.annotation.Resource;
- import org.aspectj.lang.JoinPoint;
- import org.aspectj.lang.annotation.Aspect;
- import org.aspectj.lang.annotation.Before;
- import org.aspectj.lang.reflect.MethodSignature;
- import org.springframework.data.redis.core.StringRedisTemplate;
- import org.springframework.stereotype.Component;
-
- import java.lang.annotation.Annotation;
- import java.lang.reflect.Field;
- import java.lang.reflect.Method;
- import java.time.LocalDateTime;
- import java.time.ZoneOffset;
- import java.time.format.DateTimeFormatter;
-
- /**
- * Created with IntelliJ IDEA.
- * Description:
- * User: PG
- * Date: 2024-04-16
- * Time: 18:49
- */
- @Aspect
- @Component
- public class GenerateIdAspect {
- @Resource
- private StringRedisTemplate stringRedisTemplate;
-
- // 初始时间戳
- private static final long BEGIN_TIME = 1640995200L;
-
- // 序列化位数
- private static final int BITE = 32;
-
- public Long getNext(String tableName) {
- // 1.生成时间戳
- LocalDateTime now = LocalDateTime.now();
- long nowSecond = now.toEpochSecond(ZoneOffset.UTC);
- long timestamp = nowSecond - BEGIN_TIME;
-
- // 2,生成序列化号
- String date = now.format(DateTimeFormatter.ofPattern("yyyy:MM:dd"));
- long count = stringRedisTemplate.opsForValue().increment(Keys.GENERATE_ID.getKey() + tableName + ":" + date);
-
- // 3.拼接 返回
- return Long.valueOf(timestamp << BITE | count);
- }
-
-
- @Before("execution(* com.cloud.cloud_oj_learn.mapper.*.*(..))")
- public void before(JoinPoint joinPoint) {
- // 获取方法签名
- MethodSignature methodSignature = (MethodSignature) joinPoint.getSignature();
- // 获取方法对象
- Method method = methodSignature.getMethod();
- // 获取方法参数值数组
- Object[] args = joinPoint.getArgs();
- // 获取方法注解
- Annotation[][] parameterAnnotations = method.getParameterAnnotations();
- for (int i = 0; i < parameterAnnotations.length; i++) {
- for (Annotation annotation : parameterAnnotations[i]) {
- if (annotation instanceof GenerateId) {
- try {
- // 获取参数对象
- Object arg = args[i];
- // 获取这个对象的类文件
- Class<?> clazz = arg.getClass();
- // 获取这个对象的id属性
- Field idField = clazz.getDeclaredField("id");
- // 设置字段修改权限
- idField.setAccessible(true);
- // 获取注解上的value值
- String value = ((GenerateId) annotation).value();
- // 获取该value对应的下一个id
- Long nextId = getNext(value);
- // 判断是否为空, 如果为空就赋值
- if (idField.get(arg) == null) {
- idField.set(arg, nextId);
- }
- } catch (NoSuchFieldException | IllegalAccessException e) {
- throw new RuntimeException(e);
- }
- }
- }
- }
- }
-
- }
图示
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。