业务设计——用户敏感信息展示脱敏及其反脱敏
业务需求
将用户敏感信息脱敏展示到前端是出于保护用户隐私和信息安全的考虑。
敏感信息包括但不限于手机号码、身份证号、银行卡号等,这些信息泄露可能导致用户个人信息的滥用、身份盗用等严重问题。脱敏是一种常用的保护用户隐私的方式,它的目的是减少潜在的风险,同时保持一定的用户信息可读性。
比如咱们在选择用户信息以及展示选座信息时,用户证件号码的脱敏展示。
常用脱敏规则 :替换、重排、加密、截断、掩码
Hutool 工具类实现数据脱敏
Hutool包含的组件
Hutool官方文档https://www.hutool.cn/docs/#/core/%E5%B7%A5%E5%85%B7%E7%B1%BB/%E4%BF%A1%E6%81%AF%E8%84%B1%E6%95%8F%E5%B7%A5%E5%85%B7-DesensitizedUtil
<dependency> <groupId>cn.hutool</groupId> <artifactId>hutool-all</artifactId> <version>5.8.16</version>
</dependency>注意 :Hutool 5.x支持JDK8+, 如果你的项目使用JDK7,请使用
Hutool 4.x版本。本文使用的数据脱敏工具类只有在5.6+版本以上才提供。
Hutool作为一个Java基础工具类,对文件、流、加密解密、转码、正则、线程、XML等JDK方法进行封装,组成各种Util工具类,同时提供以下组件:
可以根据需求对每个模块单独引入,也可以通过引入hutool-all方式引入所有模块,本文所使用的数据脱敏工具就是在hutool.core模块。
Hutool支持的脱敏数据类型
Hutool针对数据脱敏业务为不同的敏感数据提供了相应的API来实现脱敏操作,现阶段最新版本的Hutool支持的脱敏数据类型如下,基本覆盖了常见的敏感信息。
- 用户id
- 中文姓名
- 身份证号
- 座机号
- 手机号
- 地址
- 电子邮件
- 密码
- 中国大陆车牌,包含普通车辆、新能源车辆
- 银行卡
Hutool提供的脱敏方法如下图所示:
注意 :Hutool 脱敏是通过 * 来代替敏感信息的,具体实现是在StrUtil.hide( )方法中,如果我们想要自定义隐藏符号,则可以把Hutool的源码拷出来,重新实现即可。
API演示:
/*** 【手机号码】前三位,后4位,其他隐藏,比如135****2210** @param num 移动电话;* @return 脱敏后的移动电话;*/public static String mobilePhone(String num) {if (StrUtil.isBlank(num)) {return StrUtil.EMPTY;}return StrUtil.hide(num, 3, num.length() - 4);}/*** 【地址】只显示到地区,不显示详细地址,比如:北京市海淀区****** @param address 家庭住址* @param sensitiveSize 敏感信息长度* @return 脱敏后的家庭地址*/public static String address(String address, int sensitiveSize) {if (StrUtil.isBlank(address)) {return StrUtil.EMPTY;}int length = address.length();return StrUtil.hide(address, length - sensitiveSize, length);}/*** 【密码】密码的全部字符都用*代替,比如:******** @param password 密码* @return 脱敏后的密码*/public static String password(String password) {if (StrUtil.isBlank(password)) {return StrUtil.EMPTY;}return StrUtil.repeat('*', password.length());}
搭建Jackson序列化体系
现在有了数据脱敏工具类,如果前端需要显示数据数据的地方比较多,我们不可能在每个地方都调用一个工具类,这样就显得代码太冗余了,那我们如何通过注解的方式优雅的完成数据脱敏呢?
实现思路
在 SpringMVC 返回数据时,通过默认的 Jackson 序列化器进行指定,替换为咱们已经包装后的序列化器,这样就能依赖现有解决方案,降低技术复杂度。
代码实现
定义手机号和证件号的 Jackson 自定义序列化器,并在对应需要脱敏的敏感字段上指定自定义序列化器。
1)身份证号序列化器。
/*** 身份证号脱敏反序列化** @公众号:马丁玩编程,回复:加群,添加马哥微信(备注:12306)获取项目资料*/
public class IdCardDesensitizationSerializer extends JsonSerializer<String> {@Overridepublic void serialize(String idCard, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) throws IOException {String phoneDesensitization = DesensitizedUtil.idCardNum(idCard, 4, 4);jsonGenerator.writeString(phoneDesensitization);}
}
2)手机号序列化器。
/*** 手机号脱敏反序列化** @公众号:马丁玩编程,回复:加群,添加马哥微信(备注:12306)获取项目资料*/
public class PhoneDesensitizationSerializer extends JsonSerializer<String> {@Overridepublic void serialize(String phone, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) throws IOException {String phoneDesensitization = DesensitizedUtil.mobilePhone(phone);jsonGenerator.writeString(phoneDesensitization);}
}
3)敏感字段上自定义序列化器。
/*** 乘车人返回参数** @公众号:马丁玩编程,回复:加群,添加马哥微信(备注:12306)获取项目资料*/
@Data
@Accessors(chain = true)
public class PassengerRespDTO {/*** 证件号码*/@JsonSerialize(using = IdCardDesensitizationSerializer.class)private String idCard;/*** 手机号*/@JsonSerialize(using = PhoneDesensitizationSerializer.class)private String phone;
}
完成上述步骤后,前端调用 HTTP 请求获取数据时,SpringMVC 通过 Jackson 进行序列化数据时,操作证件号码和手机号两个字段就会采用咱们自定义的序列化器,完成敏感信息脱敏功能。
脱敏数据反脱敏
对接前端的敏感数据脱敏展示功能做到上面这些就已经实现了。但是总感觉哪里不对,因为咱们在购票服务中,下单接口会调用乘车人详细信息接口获取到手机号、证件号等信息保存入库。
如果我在后端服务里去调用乘车人的信息接口,那岂不是也是脱敏的?这样的话,存储到数据库的数据就不准确了,期望是真实的数据,但是实际是脱敏后的。为此,我们需要想办法把自己脱敏后的数据还原回来,这里介绍几种思路:
Redis缓存原始数据
将脱敏后的数据和一个随机id一起封装为个对象一起传给前端,我在redis中以这个id为key,未脱敏值为value,当前端需要基于脱敏数据进行相关操作就传个id过来让我后端在redis找到该数据的原始态
这种方案比较适用于脱敏数据较少的情况,一般对于这种敏感数据展示的需求是比较少的,但是为了实现这么个反脱敏的操作我得浪费一大块缓存取时刻保持一份热点也许相对较小的数据,一个项目的用户量上来了,他们的手机号、身份证号等等敏感数据越来越多,那这样子缓存的占比也越来越大。
对称算法加解密
这种模式的脱敏就不是运用我们前面提到的替换操作,而是一种对称加解密的过程,将敏感数据采用一个对称算法加密后传输给前端,前端将其传入到后端后再凭借对称解密的方式还原原始数据。
这种方式优点在于对称加密算法可以提供较高的安全性,只有持有密钥的人才能解密敏感数据,降低了数据泄露的风险。并且对称加解密算法通常具有较高的执行效率,可以快速地对数据进行加解密操作。但是缺点也很明显,由于对称加解密方式是全盘加密和解密,无法对敏感数据进行细粒度的控制,比如只加密部分字段或片段。并且有被拦截通过一些工具进行解码风险,从而泄露数据。
总结
本文主要介绍了数据脱敏的相关内容,首先介绍了数据脱敏的概念,在此基础上介绍了常用的数据脱敏规则;随后介绍了本文的重点Hutool工具及其使用方法,在此基础上进行了实操,分别演示了使用DesensitizedUtil工具类、配合Jackson通过注解的方式完成数据脱敏;最后,介绍了一些常见的数据反脱敏方法,本文内容如有不当之处,还请大家批评指正。
相关文章:

业务设计——用户敏感信息展示脱敏及其反脱敏
业务需求 将用户敏感信息脱敏展示到前端是出于保护用户隐私和信息安全的考虑。 敏感信息包括但不限于手机号码、身份证号、银行卡号等,这些信息泄露可能导致用户个人信息的滥用、身份盗用等严重问题。脱敏是一种常用的保护用户隐私的方式,它的目的是减少…...

Hadoop分布式安装
首先准备好三台服务器或者虚拟机,我本机安装了三个虚拟机,安装虚拟机的步骤参考我之前的一篇 virtualBox虚拟机安装多个主机访问虚拟机虚拟机访问外网配置-CSDN博客 jdk安装 参考文档:Linux 环境下安装JDK1.8并配置环境变量_linux安装jdk1.8并…...
Python——PyQt5以及Pycharm相关配置
PyQt5目录 常见的GUI框架一、安装pyqt5pip install pyqt5pip install pyqt5-tools二、Qt Designer三、在PyCharm中配置相关toolQtDisigner配置PyUIC配置PyRCC配置常见的GUI框架 Tkinter:Python内置的GUI框架,使用TCL实现,Python中内嵌了TCL解释器,使用它的时候不用安装额外…...

java集成海康预览抓图出现内存一直上涨问题
求助:在java 中集成海康sdk后批量抓图出现内存上涨问题,不论是预览后不关闭继续预览,还是预览后关闭预览,然后重新预览都没有解决这个问题(抓图正常),尝试使用第三方解码器ffmpeg来进行解码&…...

Spring Boot 使用 Disruptor 做内部高性能消息队列
这里写自定义目录标题 一 、背景二 、Disruptor介绍三 、Disruptor 的核心概念3.1 Ring Buffer3.2 Sequence Disruptor3.3 Sequencer3.4 Sequence Barrier3.5 Wait Strategy3.6 Event3.7 EventProcessor3.8 EventHandler3.9 Producer 四、案例-demo五、总结 一 、背景 工作中遇…...

一、灵动mm32单片机_开发环境的搭建(Keil)
1、安装Keil MDK。 略。 2、安装芯片对应的Pack包。 (1)这里以MM32F0130单片机为例。 (2)进入灵动微电子官网。上海灵动微电子股份有限公司 (3)点击“支持”→“KEILPacl”。 (3)点击下载Pack包。 (4)下载后,解压下载的压缩包,找到对应的Pack包&…...

【5G PHY】5G SS/PBCH块介绍(二)
博主未授权任何人或组织机构转载博主任何原创文章,感谢各位对原创的支持! 博主链接 本人就职于国际知名终端厂商,负责modem芯片研发。 在5G早期负责终端数据业务层、核心网相关的开发工作,目前牵头6G算力网络技术标准研究。 博客…...

简单而高效:使用PHP爬虫从网易音乐获取音频的方法
概述 网易音乐是一个流行的在线音乐平台,提供了海量的音乐资源和服务。如果你想从网易音乐下载音频文件,你可能会遇到一些困难,因为网易音乐对其音频资源进行了加密和防盗链的处理。本文将介绍一种使用PHP爬虫从网易音乐获取音频的方法&…...

渗透测试工具-sqlmap使用
sqlmap是一个开源渗透测试的自动化工具,可以自动检测和利用SQL注入漏洞并接管数据库服务器。它配备了一个强大的检测引擎,许多用于终极渗透测试的利基功能,以及广泛的开关,包括数据库指纹识别、从数据库中获取数据、访问底层文件系…...
C# WPF: Imag图片填充方式有哪些?
C#和WPF中的图像填充方式 在WPF中,你可以使用Image控件来显示图像,并使用不同的填充方式来控制图像在控件中的显示方式。以下是一些常见的图像填充方式: Stretch(拉伸):这是默认的填充方式,它…...

uniapp开发小程序—根据生日日期计算年龄 周岁
0、需求 在UniApp开发小程序中,将接口返回的出生日期转化为年龄;判断接口返回的年龄是否是周岁 可以使用JavaScript的日期处理方法来实现。 一、第一种方式(示例代码): //javascript // 假设接口返回的年龄为生日的…...

windows下基于vscode的ssh服务远程连接ubuntu服务器
Ubuntu端配置 1.确保ubuntu端已启用ssh服务 首先,安装ssh服务 sudo apt-get install openssh-server 安装后,打开ssh服务 sudo service ssh start 如果显示有sshd就说明成功了。 判断是否成功打开 ps -e|grep ssh 同时也可以通过如下方式确保ss…...

OpenCV学习(二)——OpenCV中绘图功能
2. OpenCV中绘图功能2.1 画线2.2 画矩形2.3 画圆2.4 画多边形2.5 添加文本 2. OpenCV中绘图功能 绘图可以实现画线、画矩形、画圆、画多边形和添加文本等操作。 import cv2 import numpy as np# 读取图像 img cv2.imread(lena.jpg)# 画直线 cv2.line(img, (0, 0), (512, 512…...

业务架构、应用架构、技术架构、数据架构
架构规划的重要性 如果没有进行合理的架构规划,将会引发一系列的问题。为了避免这些问题的发生,企业需要进行业务架构、应用架构、技术架构和数据架构的全面规划和设计,以构建一个清晰、可持续发展的企业架构。 https://www.zhihu.com/que…...

独创改进 | RT-DETR 引入 Asymptotic Hybrid Encoder | 渐进混合特征解码结构
本专栏内容均为博主独家全网首发,未经授权,任何形式的复制、转载、洗稿或传播行为均属违法侵权行为,一经发现将采取法律手段维护合法权益。我们对所有未经授权传播行为保留追究责任的权利。请尊重原创,支持创作者的努力,共同维护网络知识产权。 文章目录 网络结构实验结果…...

SpringCloudAlibaba实战-nacos集群部署
写在前面:在学习阶段,我们想快速学习SpringCloudAlibaba功能,但总是花费大量时间跟着视频或博客做组件配置。由于版本的更迭,我们学习时的组件版本很可能和作者的不一致,又或者是各自环境不一,只能一坑又一…...

Elasticsearch安装IK分词器
ik分词包 参考博客、参考博客 将下载好的zip包解压,生成一个ik文件夹 将ik文件夹移动到ES安装目录下的plugins文件夹下(每台ES节点都要执行相同的操作) 重启ES集群 坑...

『51单片机』 DS1302时钟
🚩 WRITE IN FRONT 🚩 🔎 介绍:"謓泽"正在路上朝着"攻城狮"方向"前进四" 🔎🏅 荣誉:2021|2022年度博客之星物联网与嵌入式开发TOP5|TOP4、2021|2222年获评百大…...

ubuntu部署个人网盘nextCloud使用docker-compose方式
概述 当下各大网盘的容量都是有限制的,而且xx云不开会员网速就拉跨。 所以就想搭建一个自己的盘,并且可以控制用户的权限分组; nextCloud就很合适 我这边都是自己用偶尔给其他人使用下,所以直接docker部署了。 ubuntu版本&…...

【ChatGPT 01】ChatGPT基础科普
1. 从图灵测试到ChatGPT 1950年,艾伦•图灵(Alan Turing)发表论文**《计算机器与智能》( Computing Machinery and Intelligence),提出并尝试回答“机器能否思考”这一关键问题。在论文中,图灵提出了“模仿游戏”&…...
uniapp 对接腾讯云IM群组成员管理(增删改查)
UniApp 实战:腾讯云IM群组成员管理(增删改查) 一、前言 在社交类App开发中,群组成员管理是核心功能之一。本文将基于UniApp框架,结合腾讯云IM SDK,详细讲解如何实现群组成员的增删改查全流程。 权限校验…...
[2025CVPR]DeepVideo-R1:基于难度感知回归GRPO的视频强化微调框架详解
突破视频大语言模型推理瓶颈,在多个视频基准上实现SOTA性能 一、核心问题与创新亮点 1.1 GRPO在视频任务中的两大挑战 安全措施依赖问题 GRPO使用min和clip函数限制策略更新幅度,导致: 梯度抑制:当新旧策略差异过大时梯度消失收敛困难:策略无法充分优化# 传统GRPO的梯…...

Prompt Tuning、P-Tuning、Prefix Tuning的区别
一、Prompt Tuning、P-Tuning、Prefix Tuning的区别 1. Prompt Tuning(提示调优) 核心思想:固定预训练模型参数,仅学习额外的连续提示向量(通常是嵌入层的一部分)。实现方式:在输入文本前添加可训练的连续向量(软提示),模型只更新这些提示参数。优势:参数量少(仅提…...

【配置 YOLOX 用于按目录分类的图片数据集】
现在的图标点选越来越多,如何一步解决,采用 YOLOX 目标检测模式则可以轻松解决 要在 YOLOX 中使用按目录分类的图片数据集(每个目录代表一个类别,目录下是该类别的所有图片),你需要进行以下配置步骤&#x…...

【OSG学习笔记】Day 16: 骨骼动画与蒙皮(osgAnimation)
骨骼动画基础 骨骼动画是 3D 计算机图形中常用的技术,它通过以下两个主要组件实现角色动画。 骨骼系统 (Skeleton):由层级结构的骨头组成,类似于人体骨骼蒙皮 (Mesh Skinning):将模型网格顶点绑定到骨骼上,使骨骼移动…...
大学生职业发展与就业创业指导教学评价
这里是引用 作为软工2203/2204班的学生,我们非常感谢您在《大学生职业发展与就业创业指导》课程中的悉心教导。这门课程对我们即将面临实习和就业的工科学生来说至关重要,而您认真负责的教学态度,让课程的每一部分都充满了实用价值。 尤其让我…...
#Uniapp篇:chrome调试unapp适配
chrome调试设备----使用Android模拟机开发调试移动端页面 Chrome://inspect/#devices MuMu模拟器Edge浏览器:Android原生APP嵌入的H5页面元素定位 chrome://inspect/#devices uniapp单位适配 根路径下 postcss.config.js 需要装这些插件 “postcss”: “^8.5.…...
在QWebEngineView上实现鼠标、触摸等事件捕获的解决方案
这个问题我看其他博主也写了,要么要会员、要么写的乱七八糟。这里我整理一下,把问题说清楚并且给出代码,拿去用就行,照着葫芦画瓢。 问题 在继承QWebEngineView后,重写mousePressEvent或event函数无法捕获鼠标按下事…...
C#学习第29天:表达式树(Expression Trees)
目录 什么是表达式树? 核心概念 1.表达式树的构建 2. 表达式树与Lambda表达式 3.解析和访问表达式树 4.动态条件查询 表达式树的优势 1.动态构建查询 2.LINQ 提供程序支持: 3.性能优化 4.元数据处理 5.代码转换和重写 适用场景 代码复杂性…...

FFmpeg:Windows系统小白安装及其使用
一、安装 1.访问官网 Download FFmpeg 2.点击版本目录 3.选择版本点击安装 注意这里选择的是【release buids】,注意左上角标题 例如我安装在目录 F:\FFmpeg 4.解压 5.添加环境变量 把你解压后的bin目录(即exe所在文件夹)加入系统变量…...