如何实现MyBatis中自定义参数类型转换器进行数据库字段加密与脱敏?

2026-05-24 01:331阅读0评论SEO问题
  • 内容介绍
  • 文章标签
  • 相关推荐

本文共计1356个文字,预计阅读时间需要6分钟。

如何实现MyBatis中自定义参数类型转换器进行数据库字段加密与脱敏?

目录 + 1. 问题背景 + 2. 解决方案 + 2.1 使用数据库加密算法 + 2.2 使用MyBatis的自定义参数类型转换器 + 3. 一般Web项目使用 + 3.1 创建自定义Java类型 + 3.2 自定义类的转换处理器 + 3.3 配置自定义类型和类型转换

目录
  • 1 问题背景
  • 2 解决方案
    • 2.1 使用数据库加密算法
    • 2.2 使用mybatis的自定义参数类型转换器
  • 3 一般web项目使用
    • 3.1 创建自定义Java类型
    • 3.2 自定义类的转换处理器
    • 3.3 配置自定义类型和类型转换器
    • 3.4 查询使用
    • 3.5 新增修改使用
  • 4. springboot项目使用
    • 4.1 配置自定义类型和类型转换器
    • 4.2 mybatis-plus的使用

1 问题背景

在数据库存储人员的信息时,有一些信息是敏感数据,如身份证号、出生地等。为了防止信息泄漏,这些信息不允许直接在数据库中查看,此时就需要对这些字段进行加密存储,但在页面查看的仍旧是解密后的数据。这里就涉及到加解密的问题,有两种解决方案。

2 解决方案

2.1 使用数据库加密算法

通过数据库自带的加密算法,在sql里直接使用算法加解密,这种有较多缺点,不推荐使用。

  • 写法繁琐,不易开发维护
  • 适配多种数据库时,算法难以统一,工作量也剧增

2.2 使用mybatis的自定义参数类型转换器

通过自定义Java类型和类型转换器,并在mapper.xml里标注类型,通过mybatis进行加解密。

  • 加密算法可自由选择
  • 开发维护比较简单方便
  • 不存在适配多种数据库的问题

3 一般web项目使用

3.1 创建自定义Java类型

创建一个空白类,在mapper.xml文件查询和新增修改时标注说明,表示需要mybatis进行相关类型转换。

@Alias("SecretField") public class SecretField { }

3.2 自定义类的转换处理器

这里使用国密SM4进行加解密,当然算法可自由选择别的如AES等。

@MappedTypes注解映射刚才的自定义Java类

@MappedTypes(SecretField.class) public class SecretFieldTypeHandler extends BaseTypeHandler<String> { private static final Logger log = LoggerFactory.getLogger(SecretFieldTypeHandler.class); @Override public void setNonNullParameter(PreparedStatement ps, int i, String parameter, JdbcType jdbcType) throws SQLException { try { if (StringUtils.hasText(parameter)) { String encryptStr = Sm4Util.encryptData_ECB(parameter); ps.setString(i, encryptStr); } } catch (Exception e) { ps.setString(i, parameter); log.error("mybatis加密参数异常,i:{},parameter:{}", i, parameter); } } @Override public String getNullableResult(ResultSet rs, String columnName) throws SQLException { String columnValue = rs.getString(columnName); try { if (StringUtils.hasText(columnValue)) { columnValue = Sm4Util.decryptData_ECB(columnValue); } } catch (Exception e) { log.error("mybatis解密参数异常,columnName:{}, columnValue:{}", columnName, columnValue); } return columnValue; } @Override public String getNullableResult(ResultSet rs, int columnIndex) throws SQLException { return null; } @Override public String getNullableResult(CallableStatement cs, int columnIndex) throws SQLException { return null; } }

3.3 配置自定义类型和类型转换器

这一步也可使用相关注解完成。

如何实现MyBatis中自定义参数类型转换器进行数据库字段加密与脱敏?

配置文件为mybatis的配置文件,如mybatis-config.xml。

<?xml version="1.0" encoding="UTF-8" standalone="no"?> <!DOCTYPE configuration PUBLIC "-//mybaties.org//DTD Config 3.0//EN" "mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <settings> </settings> <typeAliases> <typeAlias type="com.banxian.mybatis.alias.SecretField" alias="SecretField"/> </typeAliases> <typeHandlers> <typeHandler handler="com.banxian.mybatis.typehandler.SecretFieldTypeHandler" /> </typeHandlers> </configuration>

3.4 查询使用

查询返回需通过resultMap映射,在加密字段进行javaType指明需要的类型转换器

另外如果旧代码中结果集大量直接使用map返回,时间紧张的情况下,则可考虑写一个工具类,在service里调用进行手动解密,没得办法呀!。

<resultMap id="BaseResultMap" type="User"> <result column="sfz" property="sfz" javaType="SecretField"/> </resultMap>

3.5 新增修改使用

在设置相关参数值时,也就是在#{}里,使用javaType指明需要的类型转换器

insert into ... values(... <if test="sfz!= null"> #{sfz,jdbcType=VARCHAR,javaType=SecretField}, </if> )

4. springboot项目使用

  • 自定义类型和类型转换器代码和上面一样,这里不在赘述。
  • 项目使用了mybatis-plus插件。

4.1 配置自定义类型和类型转换器

在项目配置文件里application.yml里加上配置type-handlers-packagetype-aliases-package:分别指出你的类型转换器所在包名和自定义类所在包名。

mybatis-plus: global-config: db-config: logic-delete-field: deleted logic-not-delete-value: "0" logic-delete-value: "1" mapper-locations: "classpath*:/mapper/**/*.xml" configuration: log-impl: org.apache.ibatis.logging.stdout.StdOutImpl type-handlers-package: com.banxian.mybatis.typehandler type-aliases-package: com.banxian.mybatis.alias

4.2 mybatis-plus的使用

当然上面web项目的查询、新增和修改使用方法这里也是可以正常使用的

1)在实体类上使用注解

@TableName(autoResultMap = true)

2)在加密字段上指明类型

@TableField(value = "sfz", typeHandler = SecretFieldTypeHandler.class)

@Data @TableName(autoResultMap = true) public class User implements Serializable { private static final long serialVersionUID = 4344848828462926573L; @TableId(value = "id", type = IdType.ASSIGN_ID) private Integer id; /** * 名称 */ private String userName; /** * 是否删除 1:是 0:否 */ @TableLogic private String deleted; /** * 是否有效 1:是 0:否 */ private String valid; /** * 创建时间 */ @TableField(value = "create_at", fill = FieldFill.INSERT) private LocalDateTime createAt; /** * 更新时间 */ @TableField(value = "update_at", fill = FieldFill.INSERT_UPDATE) private LocalDateTime updateAt; @TableField(value = "sfz", typeHandler = SecretFieldTypeHandler.class) private String sfz; }

以上就是mybatis自定义参数类型转换器数据库字段加密脱敏的详细内容,更多关于mybatis数据库字段加密脱敏的资料请关注自由互联其它相关文章!

本文共计1356个文字,预计阅读时间需要6分钟。

如何实现MyBatis中自定义参数类型转换器进行数据库字段加密与脱敏?

目录 + 1. 问题背景 + 2. 解决方案 + 2.1 使用数据库加密算法 + 2.2 使用MyBatis的自定义参数类型转换器 + 3. 一般Web项目使用 + 3.1 创建自定义Java类型 + 3.2 自定义类的转换处理器 + 3.3 配置自定义类型和类型转换

目录
  • 1 问题背景
  • 2 解决方案
    • 2.1 使用数据库加密算法
    • 2.2 使用mybatis的自定义参数类型转换器
  • 3 一般web项目使用
    • 3.1 创建自定义Java类型
    • 3.2 自定义类的转换处理器
    • 3.3 配置自定义类型和类型转换器
    • 3.4 查询使用
    • 3.5 新增修改使用
  • 4. springboot项目使用
    • 4.1 配置自定义类型和类型转换器
    • 4.2 mybatis-plus的使用

1 问题背景

在数据库存储人员的信息时,有一些信息是敏感数据,如身份证号、出生地等。为了防止信息泄漏,这些信息不允许直接在数据库中查看,此时就需要对这些字段进行加密存储,但在页面查看的仍旧是解密后的数据。这里就涉及到加解密的问题,有两种解决方案。

2 解决方案

2.1 使用数据库加密算法

通过数据库自带的加密算法,在sql里直接使用算法加解密,这种有较多缺点,不推荐使用。

  • 写法繁琐,不易开发维护
  • 适配多种数据库时,算法难以统一,工作量也剧增

2.2 使用mybatis的自定义参数类型转换器

通过自定义Java类型和类型转换器,并在mapper.xml里标注类型,通过mybatis进行加解密。

  • 加密算法可自由选择
  • 开发维护比较简单方便
  • 不存在适配多种数据库的问题

3 一般web项目使用

3.1 创建自定义Java类型

创建一个空白类,在mapper.xml文件查询和新增修改时标注说明,表示需要mybatis进行相关类型转换。

@Alias("SecretField") public class SecretField { }

3.2 自定义类的转换处理器

这里使用国密SM4进行加解密,当然算法可自由选择别的如AES等。

@MappedTypes注解映射刚才的自定义Java类

@MappedTypes(SecretField.class) public class SecretFieldTypeHandler extends BaseTypeHandler<String> { private static final Logger log = LoggerFactory.getLogger(SecretFieldTypeHandler.class); @Override public void setNonNullParameter(PreparedStatement ps, int i, String parameter, JdbcType jdbcType) throws SQLException { try { if (StringUtils.hasText(parameter)) { String encryptStr = Sm4Util.encryptData_ECB(parameter); ps.setString(i, encryptStr); } } catch (Exception e) { ps.setString(i, parameter); log.error("mybatis加密参数异常,i:{},parameter:{}", i, parameter); } } @Override public String getNullableResult(ResultSet rs, String columnName) throws SQLException { String columnValue = rs.getString(columnName); try { if (StringUtils.hasText(columnValue)) { columnValue = Sm4Util.decryptData_ECB(columnValue); } } catch (Exception e) { log.error("mybatis解密参数异常,columnName:{}, columnValue:{}", columnName, columnValue); } return columnValue; } @Override public String getNullableResult(ResultSet rs, int columnIndex) throws SQLException { return null; } @Override public String getNullableResult(CallableStatement cs, int columnIndex) throws SQLException { return null; } }

3.3 配置自定义类型和类型转换器

这一步也可使用相关注解完成。

如何实现MyBatis中自定义参数类型转换器进行数据库字段加密与脱敏?

配置文件为mybatis的配置文件,如mybatis-config.xml。

<?xml version="1.0" encoding="UTF-8" standalone="no"?> <!DOCTYPE configuration PUBLIC "-//mybaties.org//DTD Config 3.0//EN" "mybatis.org/dtd/mybatis-3-config.dtd"> <configuration> <settings> </settings> <typeAliases> <typeAlias type="com.banxian.mybatis.alias.SecretField" alias="SecretField"/> </typeAliases> <typeHandlers> <typeHandler handler="com.banxian.mybatis.typehandler.SecretFieldTypeHandler" /> </typeHandlers> </configuration>

3.4 查询使用

查询返回需通过resultMap映射,在加密字段进行javaType指明需要的类型转换器

另外如果旧代码中结果集大量直接使用map返回,时间紧张的情况下,则可考虑写一个工具类,在service里调用进行手动解密,没得办法呀!。

<resultMap id="BaseResultMap" type="User"> <result column="sfz" property="sfz" javaType="SecretField"/> </resultMap>

3.5 新增修改使用

在设置相关参数值时,也就是在#{}里,使用javaType指明需要的类型转换器

insert into ... values(... <if test="sfz!= null"> #{sfz,jdbcType=VARCHAR,javaType=SecretField}, </if> )

4. springboot项目使用

  • 自定义类型和类型转换器代码和上面一样,这里不在赘述。
  • 项目使用了mybatis-plus插件。

4.1 配置自定义类型和类型转换器

在项目配置文件里application.yml里加上配置type-handlers-packagetype-aliases-package:分别指出你的类型转换器所在包名和自定义类所在包名。

mybatis-plus: global-config: db-config: logic-delete-field: deleted logic-not-delete-value: "0" logic-delete-value: "1" mapper-locations: "classpath*:/mapper/**/*.xml" configuration: log-impl: org.apache.ibatis.logging.stdout.StdOutImpl type-handlers-package: com.banxian.mybatis.typehandler type-aliases-package: com.banxian.mybatis.alias

4.2 mybatis-plus的使用

当然上面web项目的查询、新增和修改使用方法这里也是可以正常使用的

1)在实体类上使用注解

@TableName(autoResultMap = true)

2)在加密字段上指明类型

@TableField(value = "sfz", typeHandler = SecretFieldTypeHandler.class)

@Data @TableName(autoResultMap = true) public class User implements Serializable { private static final long serialVersionUID = 4344848828462926573L; @TableId(value = "id", type = IdType.ASSIGN_ID) private Integer id; /** * 名称 */ private String userName; /** * 是否删除 1:是 0:否 */ @TableLogic private String deleted; /** * 是否有效 1:是 0:否 */ private String valid; /** * 创建时间 */ @TableField(value = "create_at", fill = FieldFill.INSERT) private LocalDateTime createAt; /** * 更新时间 */ @TableField(value = "update_at", fill = FieldFill.INSERT_UPDATE) private LocalDateTime updateAt; @TableField(value = "sfz", typeHandler = SecretFieldTypeHandler.class) private String sfz; }

以上就是mybatis自定义参数类型转换器数据库字段加密脱敏的详细内容,更多关于mybatis数据库字段加密脱敏的资料请关注自由互联其它相关文章!