别再手写了!SpringBoot 6 种数据脱敏方案,第 5 种直接封神!

43 阅读4分钟

沉默是金,总会发光

大家好,我是沉默

在日常开发中,你一定遇到过这种需求:

 手机号中间四位要打星
身份证号要隐藏中间
邮箱只能露前缀
银行卡只能看头尾

比如

手机号:13812345678 → 138****5678
身份证:430101199003078888 → 430101********8888
姓名:张三四 → 张*四
邮箱:12345678@qq.com → 1234****@qq.com
银行卡:6230351888852405 → 6230********2405

于是问题来了:

  • 写在 Controller?太乱
  • 写在 Service?污染业务
  • 写在 SQL?维护地狱
  • 写在 VO?嵌套一多就炸

 这就是数据脱敏(Data Masking)

今天这篇文章,我直接把我在真实项目里用过的 6 种脱敏方案一次性讲清楚,Spring Boot 拿来就能用。

**-**01-

1-2

方案一|Hutool 工具库(懒人必备)

如果你不想造轮子,那就一句话:

直接用 Hutool

依赖

<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.8.0</version>
</dependency>

使用示例

String phone= DesensitizedUtil.mobilePhone("13812345678");
String idCard= DesensitizedUtil.idCardNum("430101199003078888"64);
String name= DesensitizedUtil.chineseName("张三四");
String email= DesensitizedUtil.email("12345678@qq.com");
String bankCard= DesensitizedUtil.bankCard("6230351888852405");
  •  开箱即用
  •  灵活性有限
  •  适合小项目 / 原型 / 快速交付

方案二|正则工具类(最直观)

不想引第三方?那就自己写工具类

 思路很简单:
输入原值 → 正则替换 → 返回脱敏值

使用方式

user.setPhone(SensitiveUtil.maskPhone(user.getPhone()));
user.setIdCard(SensitiveUtil.maskIdCard(user.getIdCard()));
  •  好理解、好调试
  •  每个地方都要手动调
  •  字段少、结构简单的场景

图片

- 02-

3-4

方案三|注解 + Jackson(工程化第一步)

很多人做到这里会开始意识到一个问题:

“我不想每个接口都手动脱敏”

那就该用 注解 + Jackson 序列化 了。

思路:

 在字段上标注
JSON 序列化时自动脱敏
业务代码 0 感知

@Sensitive(SensitiveType.PHONE)
private String phone;

优点很明显:

  •  统一出口
  •  性能好(只在序列化阶段)
  •  对嵌套对象无能为力

 但是,真正的难题出现了。

痛点|嵌套对象脱敏,前面方案全失效

来看一个真实结构

public class User {
@Sensitive(SensitiveType.PHONE)
private String phone;

private UserDetail detail;
}
public class UserDetail {
@Sensitive(SensitiveType.ID_CARD)
private String idCard;
}

结果:

  • phone  脱敏
  • detail.idCard  明文

这在真实项目里,是事故级风险

图片

- 03-

5-6

方案五|AOP 深度脱敏(架构级推荐)

 这才是中大型项目的正确解法

不是“在哪脱敏”,而是“统一在出口治理”

  • Controller / Service 返回值
  • 无论是:
    • 单对象
    • List
    • Map
    • Page
    • 多层嵌套

 全部递归处理

核心流程图

请求 → Controller → Service                ↓        AOP 环绕拦截                ↓        递归扫描返回对象                ↓               找到             @Sensitive               字段                ↓           执行脱敏                ↓             返回

效果

{
"name":"张*四",
"phone":"138****5678",
"detail":{
        "emergencyPhone":"139****8765"
    }
}

为什么我强烈推荐它?

  •  一次配置,全局生效
  •  支持任意嵌套
  •  业务代码零侵入
  •  后期统一治理

 这已经是**“安全架构层”的方案**了。

方案六|MySQL 层脱敏(DB 视角)

这是完全不同的思路

在数据库层就不让你看到明文

SELECT
  CONCAT(LEFT(phone,3),'****',RIGHT(phone,4)) AS phone
FROM users;

适合谁?

  • 报表系统
  • 只读账号
  • DBA 安全视图
  • 数据分析场景

图片

**-****04-**总结

六种方案对比表

方案优点缺点场景
Hutool不灵活小项目
工具类简单手动多少量字段
Jackson自动化不支持深层API 输出
Getter轻量重复代码VO 控制
AOP 深度脱敏⭐⭐⭐⭐⭐实现复杂中大型项目
MySQLDB 安全SQL 复杂报表

 最佳实践建议(面试 & 实战通吃)

  • 新手 / 小项目:方案一、二
  • 标准 REST API:方案三
  • 复杂对象 + 统一治理: 方案五(AOP)
  • 数据安全隔离:方案六(DB)

数据脱敏不是“字符串处理”,而是“安全架构设计”

当你的系统开始考虑:

  • 合规
  • 安全
  • 数据最小暴露原则

那你就已经不是在写 CRUD 了,而是在做 工程设计

如果这篇文章对你有帮助,
欢迎 点赞 / 收藏 / 转发

图片

**-****05-**粉丝福利

我这里创建一个程序员成长&副业交流群, 


 和一群志同道合的小伙伴,一起聚焦自身发展, 

可以聊:


技术成长与职业规划,分享路线图、面试经验和效率工具, 




探讨多种副业变现路径,从写作课程到私活接单, 




主题活动、打卡挑战和项目组队,让志同道合的伙伴互帮互助、共同进步。 




如果你对这个特别的群,感兴趣的, 
可以加一下, 微信通过后会拉你入群, 
 但是任何人在群里打任何广告,都会被我T掉。