Spring Boot中使用MyBatis-Plus和MyBatis拦截器来实现对带有特定注解的字段进行AES加密。

server/2024/10/21 2:48:03/

1. 添加依赖
首先,在pom.xml文件中添加必要的依赖项:

xml
深色版本
<dependencies>
    <!-- Spring Boot Starter Web -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>

    <!-- MyBatis-Plus Spring Boot Starter -->
    <dependency>
        <groupId>com.baomidou</groupId>
        <artifactId>mybatis-plus-boot-starter</artifactId>
        <version>3.4.3</version>
    </dependency>

    <!-- MySQL Connector -->
    <dependency>
        <groupId>mysql</groupId>
        <artifactId>mysql-connector-java</artifactId>
        <version>8.0.23</version>
    </dependency>

    <!-- AES加密库 -->
    <dependency>
        <groupId>org.apache.commons</groupId>
        <artifactId>commons-lang3</artifactId>
        <version>3.12.0</version>
    </dependency>
</dependencies>
2. 创建自定义注解
创建一个自定义注解@Encrypt,用于标记需要加密的字段:

java
深色版本
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Encrypt {
}
3. 创建AES加密工具类
创建一个AES加密工具类,用于加密和解密数据:

java
深色版本
import javax.crypto.Cipher;
import javax.crypto.spec.IvParameterSpec;
import javax.crypto.spec.SecretKeySpec;
import java.util.Base64;

public class AesUtil {

    private static final String KEY = "your-secret-key"; // 16位秘钥
    private static final String IV = "your-init-vector"; // 16位初始向量

    public static String encrypt(String value) throws Exception {
        SecretKeySpec secretKeySpec = new SecretKeySpec(KEY.getBytes(), "AES");
        IvParameterSpec ivParameterSpec = new IvParameterSpec(IV.getBytes());
        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
        cipher.init(Cipher.ENCRYPT_MODE, secretKeySpec, ivParameterSpec);
        byte[] encrypted = cipher.doFinal(value.getBytes());
        return Base64.getEncoder().encodeToString(encrypted);
    }

    public static String decrypt(String value) throws Exception {
        SecretKeySpec secretKeySpec = new SecretKeySpec(KEY.getBytes(), "AES");
        IvParameterSpec ivParameterSpec = new IvParameterSpec(IV.getBytes());
        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
        cipher.init(Cipher.DECRYPT_MODE, secretKeySpec, ivParameterSpec);
        byte[] original = cipher.doFinal(Base64.getDecoder().decode(value));
        return new String(original);
    }
}
4. 创建MyBatis拦截器
创建一个MyBatis拦截器,用于在插入数据前对带有@Encrypt注解的字段进行加密:

java
深色版本
import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.SystemMetaObject;

import java.lang.reflect.Field;

public class EncryptionInterceptor implements MetaObjectHandler {

    @Override
    public void insertFill(MetaObject metaObject) {
        try {
            Class<?> entityClass = metaObject.getOriginalObject().getClass();
            for (Field field : entityClass.getDeclaredFields()) {
                if (field.isAnnotationPresent(Encrypt.class)) {
                    field.setAccessible(true);
                    Object value = field.get(metaObject.getOriginalObject());
                    if (value != null) {
                        String encryptedValue = AesUtil.encrypt(value.toString());
                        field.set(metaObject.getOriginalObject(), encryptedValue);
                    }
                }
            }
        } catch (Exception e) {
            throw new RuntimeException("Encryption failed", e);
        }
    }

    @Override
    public void updateFill(MetaObject metaObject) {
        // 如果需要在更新时也进行加密,可以在这里实现
    }
}
5. 配置拦截器
在Spring Boot的配置类中注册拦截器:

java
深色版本
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
import com.baomidou.mybatisplus.extension.plugins.inner.PaginationInnerInterceptor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class MyBatisPlusConfig {

    @Bean
    public MybatisPlusInterceptor mybatisPlusInterceptor() {
        MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
        interceptor.addInnerInterceptor(new PaginationInnerInterceptor());
        return interceptor;
    }

    @Bean
    public EncryptionInterceptor encryptionInterceptor() {
        return new EncryptionInterceptor();
    }
}
6. 创建实体类和Mapper
创建实体类TestPayRecord,并在需要加密的字段上加上@Encrypt注解:

java
深色版本
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;

@TableName("test_pay_record")
public class TestPayRecord {

    @TableField("request_no")
    private String requestNo;

    @TableField("card_number")
    @Encrypt
    private String cardNumber;

    @TableField("card_phone")
    @Encrypt
    private String cardPhone;

    // Getters and Setters
    public String getrequestNo() {
        return requestNo;
    }

    public void setrequestNo(String requestNo) {
        this.requestNo = requestNo;
    }

    public String getCardNumber() {
        return cardNumber;
    }

    public void setCardNumber(String cardNumber) {
        this.cardNumber = cardNumber;
    }

    public String getCardPhone() {
        return cardPhone;
    }

    public void setCardPhone(String cardPhone) {
        this.cardPhone = cardPhone;
    }
}
创建Mapper接口:

java
深色版本
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.example.demo.entity.TestPayRecord;

public interface TestPayRecordMapper extends BaseMapper<TestPayRecord> {
}
7. 创建Service和Controller
创建Service类:

java
深色版本
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.example.demo.entity.TestPayRecord;
import com.example.demo.mapper.TestPayRecordMapper;
import org.springframework.stereotype.Service;

@Service
public class TestPayRecordService extends ServiceImpl<TestPayRecordMapper, TestPayRecord> {
}
创建Controller类:

java
深色版本
import com.example.demo.entity.TestPayRecord;
import com.example.demo.service.TestPayRecordService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class PaymentController {

    @Autowired
    private TestPayRecordService TestPayRecordService;

    @PostMapping("/payment")
    public String createPayment(@RequestBody TestPayRecord record) {
        TestPayRecordService.save(record);
        return "Payment record created successfully";
    }
}
8. 配置数据源
确保你在application.properties或application.yml中正确配置了数据源:

properties
深色版本
# application.properties
spring.datasource.url=jdbc:mysql://localhost:3306/your_database
spring.datasource.username=your_username
spring.datasource.password=your_password
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver

# MyBatis-Plus配置
mybatis-plus.type-aliases-package=com.example.demo.entity
mybatis-plus.mapper-locations=classpath:mapper/*.xml
9. 启动应用
启动Spring Boot应用,并使用Postman或其他工具发送POST请求来测试插入功能:

json
深色版本
{
    "requestNo": "123456",
    "cardNumber": "1234567890123456",
    "cardPhone": "13800000000"
}
这样,cardNumber和cardPhone字段在插入数据库之前会被自动加密。


http://www.ppmy.cn/server/133515.html

相关文章

给定数组找出出现次数超过数组长度一半的数

&#x1f381;&#x1f449;点击进入文心快码 Baidu Comate 官网&#xff0c;体验智能编码之旅&#xff0c;还有超多福利&#xff01;&#x1f381; 【大厂面试真题】系列&#xff0c;带你攻克大厂面试真题&#xff0c;秒变offer收割机&#xff01; ❓今日问题&#xff1a;给定…

10月18日,每日信息差

第一、现代汽车集团在上海举办了中国前瞻技术研发中心的发布及启新庆典&#xff0c;宣布成立其全资法人公司 —— 现代前瞻汽车技术开发&#xff08;上海&#xff09;有限公司。该中心是集团在海外建立的首个前瞻技术研发中心&#xff0c;专注于自动驾驶、智能座舱、共享出行等…

卷积神经网络(CNN)-Padding介绍

在卷积过程中,输出特征图的大小由输入特征图的大小、内核的大小和步幅决定。如果我们简单地在输入特征图上应用内核,那么输出特征图将小于输入。这可能会导致输入特征图边界处的信息丢失。为了保留边框信息,我们使用padding。 什么是填充 Padding是一种技术,用于在对特征…

MySQL 【日期】函数大全(七)

目录 1、UNIX_TIMESTAMP() 将指定的日期/日期时间转为 UNIX 时间戳值。 2、WEEK() 返回给定日期位于当年的第几周。 3、WEEKDAY() 返回给定日期的工作日编号。 4、WEEKOFYEAR() 返回给定日期位于当年的第几周 5、YEAR() 提取日期的年份部分并作为数字返回。 6、YEARWEEK()…

通过Spring AI 调用通义千问国产大模型_基于Spring AI Alibaba

通义千问介绍 我们可以通过Spring最新推出的Spring AI 框架 来调用通义千问国产大模型。这种集成可以有效的帮助我们过去的系统更智能&#xff0c;还能显著提升用户体验&#xff0c;我将以一个详细的示例进行说明。 通义千问是由国内领先的人工智能企业研发的一款强大语言模型…

基于SpringBoot+Vue+uniapp微信小程序的乡村政务服务系统的详细设计和实现(源码+lw+部署文档+讲解等)

项目运行截图 技术框架 后端采用SpringBoot框架 Spring Boot 是一个用于快速开发基于 Spring 框架的应用程序的开源框架。它采用约定大于配置的理念&#xff0c;提供了一套默认的配置&#xff0c;让开发者可以更专注于业务逻辑而不是配置文件。Spring Boot 通过自动化配置和约…

【v5.3.0】修复订单批量发货提示 isPicUpload is not defined

使用订单批量发货的时候&#xff0c;没有反应&#xff0c;控制台提示 ReferenceError: isPicUpload is not defined 修改文件src/pages/order/orderList/components/tableList.vue 把isPicUpload改成isFileUpload&#xff0c;然后重新打包admin后台上传即可

redhat系列的yum源配置

一、Linux更改yum源为阿里云源 一&#xff09;原yum源备份 cp -rp /etc/yum.repos.d/CentOS-Base.repo{,.bak} cp -rp /etc/yum.repos.d/epel.repo{,.bak} 二&#xff09;更改为阿里云源  1、更改yum base源 下载新的CentOS-Base.repo 到/etc/yum.repos.d/ http://mirrors.al…