利用fastjson序列化实现数据脱敏

个人博客纯净版

利用fastjson序列化实现数据脱敏 | 代码搬运工

首先定义脱敏类型枚举类

public enum SensitiveType {
    /**
     * 中文名
     */
    CHINESE_NAME,
    /**
     * 手机号
     */
    MOBILE_PHONE;
}

定义脱敏注解

@Retention(RetentionPolicy.RUNTIME)
@JacksonAnnotationsInside
public @interface SensitiveInfo {
  public SensitiveType value();
}

定义脱敏拦截器

@Slf4j
public class ValueDesensitizeFilter implements ValueFilter {

    @Override
    public Object process(Object object, String name, Object value) {
        if (ObjectUtils.isEmpty(value) || !(value instanceof String)) {
            return value;
        }

        try {
            Field field = object.getClass().getDeclaredField(name);
            SensitiveInfo sensitiveInfo = field.getAnnotation(SensitiveInfo.class);
            if (String.class != field.getType() || ObjectUtils.isEmpty(sensitiveInfo)) {
                return value;
            }
            String originVal = String.valueOf(value);
            SensitiveType sensitiveType = sensitiveInfo.value();
            switch (sensitiveType) {
                case CHINESE_NAME:
                    return SensitiveInfoUtils.chineseName(originVal);
                case MOBILE_PHONE:
                    return SensitiveInfoUtils.mobilePhone(originVal);
                default:
            }
        } catch (NoSuchFieldException e) {
            log.error("当前数据类型为{},值为{}", object.getClass(), value);
        }

        return value;
    }
}

fastjson序列化配置类

import com.alibaba.fastjson.serializer.SerializerFeature;
import com.alibaba.fastjson.support.config.FastJsonConfig;
import com.alibaba.fastjson.support.spring.FastJsonHttpMessageConverter;
import org.springframework.boot.autoconfigure.http.HttpMessageConverters;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.MediaType;
import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import java.util.ArrayList;
import java.util.List;

@Configuration
public class WebConfigurer implements WebMvcConfigurer {

    /**
     * 配置fastjson为默认JSON转换
     * @return
     */
    @Bean
    public HttpMessageConverters fastJsonHttpMessageConverters() {
        // 1.定义一个converters转换消息的对象
        FastJsonHttpMessageConverter fastConverter = new FastJsonHttpMessageConverter();
        // 2.添加fastjson的配置信息,比如: 是否需要格式化返回的json数据
        FastJsonConfig fastJsonConfig = new FastJsonConfig();
        fastJsonConfig.setSerializerFeatures(SerializerFeature.PrettyFormat);
        // 中文乱码解决方案
        List<MediaType> mediaTypes = new ArrayList<>();
        mediaTypes.add(MediaType.APPLICATION_JSON_UTF8);//设定json格式且编码为UTF-8
        fastConverter.setSupportedMediaTypes(mediaTypes);
        fastJsonConfig.setSerializeFilters(new ValueDesensitizeFilter());//添加自己写的拦截器
        // 3.在converter中添加配置信息
        fastConverter.setFastJsonConfig(fastJsonConfig);
        // 4.将converter赋值给HttpMessageConverter
        HttpMessageConverter<?> converter = fastConverter;
        // 5.返回HttpMessageConverters对象
        return new HttpMessageConverters(converter);
    }
}

脱敏工具类

public class SensitiveInfoUtils {

    public static String chineseName(final String fullName) {
        if (StringUtils.isBlank(fullName)) {
            return "";
        }

        final String name = StringUtils.left(fullName, 1);
        return StringUtils.rightPad(name, StringUtils.length(fullName), "*");
    }

    public static String mobilePhone(final String phone) {
        if (StringUtils.isBlank(phone)) {
            return "";
        }
        return phone.replaceAll("(\\d{3})\\d{4}(\\d{4})", "$1****$2");
    }

}

需要脱敏的实体类

@Setter
@Getter
@NoArgsConstructor
@AllArgsConstructor
public class User {

    private Integer id;

    @SensitiveInfo(SensitiveType.CHINESE_NAME)
    private String username;

    @SensitiveInfo(SensitiveType.MOBILE_PHONE)
    private String phone;

    private String password;
}

需要脱敏的实体字段,需要脱敏的字段需要添加@SensitiveInfo注解,并指定脱敏类型。以上脱敏只能实现接口数据脱敏,要想实现利用fastjson数据传输时实时脱敏改如何实现呢?具体实现方式如下:

User user = new User();
user.setId(1);
user.setUsername("张三");
user.setPhone("18700370977");

ValueDesensitizeFilter filter = new ValueDesensitizeFilter();
String jsonString = JSON.toJSONString(user, filter);

对象在通过fastjson序列化时指定脱敏过滤器,就可以实现实时脱敏了,拿到jsonString已经是脱敏后的json串

  • 2
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Fastjson是一种高性能的Java JSON处理器。它提供了很多方便的功能,包括数据脱敏数据脱敏是指在保护数据的机密性和隐私性的前提下,对敏感数据进行部分隐藏或替换,以避免敏感信息泄露。Fastjson可以通过自定义序列器和反序列器,实现数据脱敏处理。 下面是一个简单的例子,演示如何使用Fastjson实现数据脱敏: ```java public class User { private String name; private String idCard; private String phone; // 省略getter和setter方法 // 自定义序列器,对身份证号进行脱敏处理 public static class IdCardSerializer implements ObjectSerializer { @Override public void write(JSONSerializer serializer, Object object, Object fieldName, Type fieldType, int features) throws IOException { String idCard = (String) object; if (idCard == null || idCard.isEmpty()) { serializer.writeNull(); } else { String maskedIdCard = idCard.replaceAll("(\\d{4})\\d{10}(\\w{4})", "$1**********$2"); serializer.write(maskedIdCard); } } } // 自定义反序列器,对身份证号进行解密处理 public static class IdCardDeserializer implements ObjectDeserializer { @Override public <T> T deserialze(DefaultJSONParser parser, Type type, Object fieldName) { String idCard = parser.parseObject(String.class); if (idCard == null || idCard.isEmpty()) { return null; } else { return (T) decrypt(idCard); // 解密身份证号 } } @Override public int getFastMatchToken() { return JSONToken.LITERAL_STRING; } private String decrypt(String idCard) { // 解密身份证号 return idCard; } } } ``` 在上面的例子中,我们定义了一个User类,包含了name、idCard和phone三个属性。我们通过自定义序列器和反序列器,对idCard进行脱敏处理和解密处理。 在序列时,我们使用了自定义的IdCardSerializer序列器对idCard进行脱敏处理,将其中的中间10位数字替换成星号。在反序列时,我们使用了自定义的IdCardDeserializer反序列器对idCard进行解密处理,将加密的身份证号转换成明文身份证号。 当我们需要序列User对象时,只需要将User对象传给Fastjson的toJSONString方法即可: ```java User user = new User(); user.setName("张三"); user.setIdCard("110101199001011234"); user.setPhone("13888888888"); String jsonString = JSON.toJSONString(user); System.out.println(jsonString); ``` 输出结果为: ```json {"idCard":"1101**********1234","name":"张三","phone":"13888888888"} ``` 可以看到,idCard已经被脱敏处理了。 当我们需要反序列JSON字符串时,只需要将JSON字符串传给Fastjson的parseObject方法即可: ```java String jsonString = "{\"idCard\":\"1101**********1234\",\"name\":\"张三\",\"phone\":\"13888888888\"}"; User user = JSON.parseObject(jsonString, User.class); System.out.println(user.getIdCard()); ``` 输出结果为: ```java 110101199001011234 ``` 可以看到,idCard已经被成功解密了。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值