mybatis、mybatis-plus自定义插件,实现自定义策略数据脱敏功能

news2024/11/10 11:38:06

背景

mybatis中四大组件的作用,下面开发的插件拦截器会使用
四大组件Executor、StatementHandler、ParameterHandler、ResultSetHandler
在这里插入图片描述

需求

1、根据脱敏规则进行查询数据,显示的时候进行展示脱敏
2、根据脱敏规则进行查询数据,将脱敏后的数据批量更新回数据库,进行脱敏存储

数据

在这里插入图片描述

/*
 Navicat Premium Data Transfer

 Source Server         : localhost
 Source Server Type    : MySQL
 Source Server Version : 80026 (8.0.26)
 Source Host           : localhost:3306
 Source Schema         : mp

 Target Server Type    : MySQL
 Target Server Version : 80026 (8.0.26)
 File Encoding         : 65001

 Date: 18/08/2024 13:44:24
*/

SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;

-- ----------------------------
-- Table structure for user
-- ----------------------------
DROP TABLE IF EXISTS `user`;
CREATE TABLE `user`  (
  `id` bigint NOT NULL AUTO_INCREMENT COMMENT '用户id',
  `username` varchar(50) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '用户名',
  `password` varchar(128) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '密码',
  `phone` varchar(20) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '注册手机号',
  `info` json NOT NULL COMMENT '详细信息',
  `status` int NULL DEFAULT 1 COMMENT '使用状态(1正常 2冻结)',
  `balance` int NULL DEFAULT NULL COMMENT '账户余额',
  `create_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间',
  `update_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
  PRIMARY KEY (`id`) USING BTREE,
  UNIQUE INDEX `username`(`username` ASC) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 5 CHARACTER SET = utf8 COLLATE = utf8_general_ci COMMENT = '用户表' ROW_FORMAT = COMPACT;

-- ----------------------------
-- Records of user
-- ----------------------------
INSERT INTO `user` VALUES (1, 'Jack', 'D5F3C4C80A651CFE876DA231061FA871', '13900112224', '{\"age\": 20, \"intro\": \"佛系青年\", \"gender\": \"male\"}', 1, 1600, '2023-05-19 20:50:21', '2024-08-18 13:43:05');
INSERT INTO `user` VALUES (2, 'Rose', 'D5F3C4C80A651CFE876DA231061FA871', '13900112223', '{\"age\": 19, \"intro\": \"青涩少女\", \"gender\": \"female\"}', 1, 600, '2023-05-19 21:00:23', '2024-08-18 13:43:09');
INSERT INTO `user` VALUES (3, 'Hope', 'D5F3C4C80A651CFE876DA231061FA871', '13900112222', '{\"age\": 25, \"intro\": \"上进青年\", \"gender\": \"male\"}', 1, 100000, '2023-06-19 22:37:44', '2024-08-18 13:43:12');
INSERT INTO `user` VALUES (4, 'Toomas', 'D5F3C4C80A651CFE876DA231061FA871', '17701265258', '{\"age\": 29, \"intro\": \"伏地魔\", \"gender\": \"male\"}', 1, 800, '2023-06-19 23:44:45', '2024-08-18 13:43:27');

SET FOREIGN_KEY_CHECKS = 1;

具体实现

1、定义脱敏规则

mybatis:
  interceptors:
#    是否开启拦截
    enabled: true
desensitization:
#  是否进行脱敏
  enabled: true
  rule:
#    脱敏模式
    - schema: MP
#      是否全模式脱敏
      allSchema: true
#      单模式脱敏规则
      schemaRule:
#        模式下需要脱敏的表
        - tableName: USER
#          模式下需要脱敏的表的主键字段
          keyColumn: id
#          具体表的脱敏规则
          tableRule:
#            具体列的脱敏规则
            - column: username
              columnRule:
#                隐藏脱敏,*代替
                ruleType: hide
                startIndex: 1
                endIndex: 2
            - column: password
              columnRule:
#                密码aes加密脱敏
                ruleType: aes
#      全模式脱敏规则
      allTableRule:
        - column: username
          columnRule:
            ruleType: hide
            startIndex: 1
            endIndex: 2
        - column: password
          columnRule:
#             密码aes加密脱敏
              ruleType: aes

2、配置类

/**
 * @author code
 * @version 1.0
 * @Date 2024/8/16 13:35
 * @Description ${DESCRIPTION}
 */
@Data
@Component
@ConfigurationProperties(prefix = "desensitization")
public class DesensitizationConfig {
   

    private String enabled = "false";

    private List<DesensitizationBaseRule> rule;
}
/**
 * @author code
 * @version 1.0
 * @Date 2024/8/16 13:37
 * @Description 脱敏规则
 */
@Data
@EqualsAndHashCode(callSuper = false)
@NoArgsConstructor
public class DesensitizationBaseRule implements Serializable {
   
    private static final long serialVersionUID = 1L;

    private String schema = "schema";

    private String allSchema = "false";

    private List<DesensitizationSchemaRule> schemaRule = new ArrayList<>();

    private List<DesensitizationTableRule> allTableRule = new ArrayList<>();
}
/**
 * @author code
 * @version 1.0
 * @Date 2024/8/16 13:41
 * @Description ${DESCRIPTION}
 */
@Data
@EqualsAndHashCode(callSuper = false)
@NoArgsConstructor
public class DesensitizationSchemaRule implements Serializable {
   
    private static final long serialVersionUID = 1L;

    private String tableName = "table";

    private String keyColumn = "id";

    private List<DesensitizationTableRule> tableRule;

}
/**
 * @author code
 * @version 1.0
 * @Date 2024/8/16 13:46
 * @Description ${DESCRIPTION}
 */
@Data
@EqualsAndHashCode(callSuper = false)
@NoArgsConstructor
public class DesensitizationTableRule implements Serializable {
   

    private static final long serialVersionUID = 1L;

    private String column = "name";

    private DesensitizationMaskRule columnRule;
}
/**
 * @author code
 * @version 1.0
 * @Date 2024/8/16 13:50
 * @Description ${DESCRIPTION}
 */
@Data
@EqualsAndHashCode(callSuper = false)
@NoArgsConstructor
public class DesensitizationMaskRule implements Serializable {
   

    private static final long serialVersionUID = 1L;

    private String ruleType = "hide";

    private int startIndex = 1;

    private int endIndex = 2;
}

3、拦截器

/**
 * @author code
 * @version 1.0
 * @Date 2024/8/13 9:54
 * @Description ${DESCRIPTION}
 */
@Intercepts({
   
        @Signature(type = StatementHandler.class, method = "prepare", args = {
   Connection.class, Integer.class})
})
@Slf4j
public class SqlQueryInterceptor implements Interceptor {
   

    private static final Pattern TABLE_NAME_PATTERN = Pattern.compile("(FROM|UPDATE)\\s+([\\w\\._]+)");

    @Override
    public Object plugin(Object target) {
   
        return Plugin.wrap(target, this);
    }

    @Override
    public void setProperties(Properties properties) {
   

    }

    @Override
    public Object intercept(Invocation invocation) throws Throwable {
   
        StatementHandler statementHandler = (StatementHandler)invocation.getTarget();

        // 获取连接对象
        Connection connection = (Connection) invocation.getArgs()[0];
        // 获取数据库名称
        String databaseName = connection.getCatalog();
        log.info("----------当前数据库名:{}", databaseName);

        Object parameterObject = statementHandler.getParameterHandler().getParameterObject();
        JSONObject paramObject = JSONObject.parseObject(JSON.toJSONString(parameterObject));

        BoundSql boundSql = statementHandler.getBoundSql();
        //统一转大写
        String tableNameSql = boundSql.getSql().toUpperCase();
        //获取表名
        String tableNa

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2050406.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【Python系列】 Python打印99乘法表

&#x1f49d;&#x1f49d;&#x1f49d;欢迎来到我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里可以感受到一份轻松愉快的氛围&#xff0c;不仅可以获得有趣的内容和知识&#xff0c;也可以畅所欲言、分享您的想法和见解。 推荐:kwan 的首页,持续学…

Vue+ElementUI技巧分享:创建一个带有进度显示的文件下载和打包组件

在现代前端开发中&#xff0c;用户体验至关重要&#xff0c;尤其是在处理文件下载时。为用户提供实时的下载进度显示和打包功能&#xff0c;不仅能提升用户体验&#xff0c;还能使应用更具专业性。在本文中&#xff0c;我们将创建一个 Vue 组件&#xff0c;用于显示文件下载进度…

视图变化 - 等比例变换防止视图拉伸

文章目录 使用场景等比变换等高填充等宽填充代码进行比目标宽高计算超出部分处理设置负的 marginclip 裁剪 End参考&#xff1a; 使用场景 在日常开发中&#xff0c;经常会遇到的一个需求是将图片/视频从界面的一个位置&#xff0c;变换到另一个位置。在处理这类问题的时候经常…

基于微信小程序的书籍销售预测系统的设计与实现(论文+源码)_kaic

摘 要 随着信息化社会的进步&#xff0c;我们的生活越来越便利。在网上&#xff0c;我们可以轻松地进行各种交易&#xff0c;其中包括图书交易。可以说&#xff0c;图书交易是网络交易的一个重要方面。本系统以面向对象的方式进行开发&#xff0c;使用MySQL作为主要数据存储…

linux centos stream9图形化操作

初学者对图形化操作比较熟悉,对字符界面、命令行比较陌生。本文讨论一下图形化操作的基本技能。希望初学者掌握后尽快使用字符界面,会执行命令,更会编程。 本案例是基于stream9版本,如版本不同,会有差别,注意操作使用。 一、安装图形化界面 Linux操作系统常用的图形用…

Unity URP无光照下Shadow 制作 <二> 合批处理

闲谈 相信大家在日常工作中发现了一个问题 &#xff0c; urp下虽然可以做到3个Pass 去写我们想要的效果&#xff0c;但是&#xff0c;不能合批&#xff08;不能合批&#xff0c;那不是我们CPU要干冒烟~&#xff01;&#xff09; 好家伙&#xff0c;熊猫老师的偏方来了 &#x…

Leetcode JAVA刷刷站(38)外观数列

一、题目概述 二、思路方向 为了解决这个问题&#xff0c;我们可以编写一个Java函数countAndSay&#xff0c;该函数接受一个整数n作为输入&#xff0c;并返回外观数列的第n个元素。这个函数将基于递归公式来构建数列&#xff0c;其中countAndSay(1) "1"&#xff0c;…

vue设置环境变量

1、在根目录地下建立两个文件&#xff0c;.env.development 和 .env.production VUE_APP_BASE_API"" .env.development这个就是开发环境&#xff0c;.env.production这个就是生产环境&#xff0c;也就是这个可以写本地的ip端口 .env.production 这个就是生产环境&…

Verilog刷题笔记51

题目&#xff1a; Now that you have a state machine that will identify three-byte messages in a PS/2 byte stream, add a datapath that will also output the 24-bit (3 byte) message whenever a packet is received (out_bytes[23:16] is the first byte, out_bytes[1…

14、springboot3 vue3开发平台-前端-自定义菜单组件,根据路由动态渲染

文章目录 1. 组件2 . 使用示例 1. 组件 src\components\menuTree\index.vue <template><template v-for"item in menuList"><!-- 分为两种方式渲染&#xff1a;有子菜单和没有子菜单--><!-- 没有子菜单--><el-menu-item :index&qu…

linux cpu问题排查及性能优化

cpu性能 一、cpu啥时候才叫有瓶颈 cpu运行的快还是慢、cpu有没有问题&#xff0c;cpu是不是还需要优化。这些是平常开发和运维中经常遇到的问题。那么我门到底如何去判断机器cpu运行的到底有没有异常呢。 从我排查问题来说&#xff0c;单看系统指标不能完全反应应用运行的状态…

移动魔百盒刷机教程

准备工作 确认型号&#xff1a;首先确认您的魔百盒的具体型号&#xff0c;不同的型号可能需要不同的刷机包。刷机包&#xff1a;下载适合您型号的刷机包。U盘&#xff1a;准备一个容量不超过8GB的U盘&#xff0c;并将其格式化为FAT32格式。刷机工具&#xff1a;根据型号可能需…

深度学习实战:手把手教你构建多任务、多标签模型

多任务多标签模型是现代机器学习中的基础架构&#xff0c;这个任务在概念上很简单 -训练一个模型同时预测多个任务的多个输出。 在本文中,我们将基于流行的 MovieLens 数据集,使用稀疏特征来创建一个多任务多标签模型,并逐步介绍整个过程。所以本文将涵盖数据准备、模型构建、训…

keepalived讲解及练习

目录 1、keepalived介绍 1.1 keepalived简介 2、高可用集群 2.1 集群类型 2.2 系统可用性 2.3 系统故障 2.4 实现高可用 3、VRRP 3.1 VRRP&#xff1a;Virtual Router Redundancy Protocol 3.2 VRRP 相关术语 3.3 VRRP相关技术 4、 keepalived实验 4.1 全局配置 4…

Vue封装axios请求(超详细)

一、简介 Vue封装axios请求是指将axios库集成到Vue项目中&#xff0c;以便更方便地发送HTTP请求。首先&#xff0c;需要安装axios库&#xff0c;然后在Vue项目中创建一个名为request.js的文件&#xff0c;用于封装axios实例。在这个文件中&#xff0c;可以设置默认的配置&#…

fastzdp_sqlmodel框架是如何实现更新和删除相关的功能封装的,20240817,Python的国产新ORM框架

根据模型对象更新 初步封装的方法 def update(engine, model_obj, update_dict):"""修改数据:param engine: 连接数据库的引擎对象:param model_obj: 模型对象:param update_dict: 更新字典:return:"""with Session(engine) as session:if not…

Git工具详细使用教程

Git工具详细使用教程 Git是一个分布式版本控制系统&#xff0c;它可以帮助你管理代码的历史记录。本教程将介绍如何使用Git工具进行基本的版本控制操作。 1. 安装Git 首先&#xff0c;你需要在你的计算机上安装Git。你可以从Git官方网站&#xff08;https://git-scm.com/&am…

MySQL(三)——DCL

文章目录 DCL用户管理查询用户创建用户修改用户密码删除用户 权限控制查询权限授予权限撤销权限 DCL DCL&#xff08;Data Control Language&#xff0c;数据控制语言&#xff09;是SQL的一个子集&#xff0c;专门用于定义数据库、表、视图等的访问权限和安全级别。 它允许数据…

Openstack二层网络的构建和使用

Openstack二层网络的构建和使用 一、实验目的 &#xff08;1&#xff09;了解网络层级、子网、动态地址、网关代理等概念并进行应用。 &#xff08;2&#xff09;了解OpenStack项目以及相关组件。 &#xff08;3&#xff09;了解 Neutron 二层网络的构建和使用。 二、实验原…

如何确定vtk .h文件所在的库名字

问题 例如使用class vtkSTLReader,头文件包含#include <vtkSTLReader.h>,库使用哪个&#xff1f; 解决 1.在vs2019解决方案资源管理器中搜索vtkSTLReader.cxx&#xff0c;显示project为IOGeometry即为库名 2.在所在的CMakeLists.txt追加库名 3.在cmake重新Configure、G…