公共字段自动填充功能实现【springboot】

问题分析

很多业务表里面有相同的公共字段,导致每次插入都要写相同的代码,代码冗余,不便于后期维护

公共字段填充是解决​​重复性字段统一管理​​问题的技术方案,主要用于自动处理实体类中那些在多处重复出现且赋值逻辑相同的字段(如创建时间、创建人、更新时间等)。

解决思路

代码实现

1,自定义注解

指定添加注解的地方

2,自定义切面类。切面=切入点+通知

定义切入点,确定切入点位置

定义通知,确定通知类型,通知要执行的操作

3,先给需要自动装配的方法加上注解,测试一下,再写通知操作

通知要执行的操作

1,获取方法对数据库操作类型,确定要填充的字段

  • 利用方法签名对象和反射获取注解对象

2,获取当前拦截的方法的参数(实体对象)

  • 判断防止出现空指针,接收对象用object最好

3,准备要赋值的数据

  • 利用ThreadLocal和其他工具类

4,根据不同的数据库操作类型,利用反射进行赋值

  • 利用反射获取需要装配的字段的set方法。
  • 利用invoke方法进行赋值。invoke()反射核心方法,第一个参数是调用对象实例,后续是方法参数。
java 复制代码
//指定注解只能加在方法上
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface AutoFill {
    //数据库操作类型;update insert
    //指定当前数据库操作类型是更新还是插入,只有在插入或者更新的时候才需要自动填充功能
    OperationType value();
}
java 复制代码
@Aspect
@Component
@Slf4j
public class AutoFillAspect {
    /*
     * 切入点
     * */

    @Pointcut("execution(* com.sky.mapper.*.*(..)) && @annotation(com.sky.annotation.AutoFill)")
    public void autoFillPointCut() {

    }

    /*
    前置通知,在通知中进行公共字段的填充
    */
    @Before("autoFillPointCut()")
    public void autoFill(JoinPoint joinPoint) {
        log.info("开始进行公共字段填充");
        //获取当前被拦截数据库操作的类型
        MethodSignature signature = (MethodSignature) joinPoint.getSignature();//方法前面对象
        AutoFill autoFill = signature.getMethod().getAnnotation(AutoFill.class);//获得方法上的注解对象
        OperationType operationType = autoFill.value(); //获得数据库操作类型

        //获取当前被拦截的方法的参数
        Object[] args = joinPoint.getArgs();
        if (args == null || args.length == 0) {
            return;
        }
        Object entity = args[0];
        //准备赋值的数据
        LocalDateTime now = LocalDateTime.now();
        Long currentId = BaseContext.getCurrentId();
        //根据不同的操作类型,为对应的属性赋值
        if (operationType == OperationType.INSERT) {
            //为四个公共字段赋值
            try {
                Method setCreateTime = entity.getClass().getDeclaredMethod(AutoFillConstant.SET_CREATE_TIME, LocalDateTime.class);
                Method setCreateUser = entity.getClass().getDeclaredMethod(AutoFillConstant.SET_CREATE_USER, Long.class);
                Method setUpdateTime = entity.getClass().getDeclaredMethod(AutoFillConstant.SET_UPDATE_TIME, LocalDateTime.class);
                Method setUpdateUser = entity.getClass().getDeclaredMethod(AutoFillConstant.SET_UPDATE_USER, Long.class);

                //通过反射为对象属性赋值
                setCreateTime.invoke(entity, now);
                setCreateUser.invoke(entity, currentId);
                setUpdateTime.invoke(entity, now);
                setUpdateUser.invoke(entity, currentId);
            } catch (Exception e) {
                throw new RuntimeException(e);
            }


        } else if (operationType == OperationType.UPDATE) {
            //为两个公共字段赋值
            try {
                Method setUpdateTime = entity.getClass().getDeclaredMethod(AutoFillConstant.SET_UPDATE_TIME, LocalDateTime.class);
                Method setUpdateUser = entity.getClass().getDeclaredMethod(AutoFillConstant.SET_UPDATE_USER, Long.class);
                //通过反射为对象属性赋值
                setUpdateTime.invoke(entity, now);
                setUpdateUser.invoke(entity, currentId);
            } catch (Exception e) {
                throw new RuntimeException(e);
            }

        }
    }
}
相关推荐
一只小白0006 分钟前
数据库对象实例化流程模板 + 常见错误
数据库
一江寒逸18 分钟前
零基础从入门到精通MySQL(下篇):精通篇——吃透索引底层、锁机制与性能优化,成为MySQL实战高手
数据库·mysql·性能优化
DevOpenClub23 分钟前
全国三甲医院主体信息 API 接口
java·大数据·数据库
一勺菠萝丶33 分钟前
管理后台使用手册在线预览与首次登录引导弹窗实现
java·前端·数据库
无忧智库36 分钟前
某大型银行“十五五”金融大模型风控与智能投顾平台建设方案深度解读(WORD)
数据库·金融
爱码小白38 分钟前
数据库多表命名的通用规范
数据库·python·mysql
huohuopro1 小时前
Hbase伪分布式远程访问配置
数据库·分布式·hbase
XDHCOM1 小时前
ORA-12169: TNS连接标识符过长,Oracle报错故障修复与远程处理
数据库·oracle
爬山算法1 小时前
MongoDB(86)如何使用MongoDB存储大文件?
数据库·mongodb
xcLeigh2 小时前
KES数据库表空间目录自动创建特性详解与存储运维最佳实践
大数据·运维·服务器·数据库·表空间·存储