最近老大想作一个日志脱敏的需求,看了网上的一些方案都不太满意,可是仍是借鉴了一些网上的代码实现了该功能java
实现原理很简单就是重写了 fastjson ValueFilter.class process方法git
在实体上标明须要脱敏的字段json
打印日志时使用自定义公共脱敏方法 输出日志测试
举例 spa
1:@SensitiveAnn(type = SensitiveTypeEnum.PHONE) .net
2:SensitiveInfoUtils.toJsonString(cardInfo)日志
https://gitee.com/shiliang_feng/codes/iqlnwjsezh53umbpag8vx88code
定义一个@interface Ann 里面有一个自定义枚举的属性blog
import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; import com.demo.enums.SensitiveTypeEnum; /** * * @ClassName: SensitiveAnn * @Description:脱敏字段注解 * @author shiliang.feng * @date 2019年8月16日 下午5:11:20 * */ @Target({ ElementType.TYPE, ElementType.FIELD }) @Retention(RetentionPolicy.RUNTIME) public @interface SensitiveAnn { SensitiveTypeEnum type(); }
枚举的代码以下ip
public enum SensitiveTypeEnum { /** 身份证号码 */ ID_CARD, /** 银行卡号 */ BANK_CARD, /** 手机号码 */ PHONE, /** 名字 */ NAME, /** 邮箱 */ EMAIL }
/** * * @Title: mobilePhone * @Description: [手机号码] 前三位,后两位,其余隐藏<例子:138********34> * @author 1100122 * @date 2019年3月22日 下午7:56:10 * @param num * @return * @throws */ public static String mobilePhone(String num) { if (StringUtils.isBlank(num)) { return ""; } return StringUtils.left(num, 3).concat(StringUtils.removeStart(StringUtils.leftPad(StringUtils.right(num, 2), StringUtils.length(num), "*"), "***")); } /** * * @Title: idCardNum * @Description: [身份证号] 显示前六位,最后两位,其余隐藏。共计18位或者15位。<例子:152728*********62> * @author 1100122 * @date 2019年3月22日 下午7:56:03 * @param num * @return * @throws */ public static String idCardNum(String num) { if (StringUtils.isBlank(num)) { return ""; } return StringUtils.left(num, 6).concat(StringUtils.removeStart(StringUtils.leftPad(StringUtils.right(num, 2), StringUtils.length(num), "*"), "******")); } /** * * @Title: bankCard * @Description:[银行卡号] 前六位,后四位,其余用星号隐藏每位1个星号<例子:6222600**********1234> * @author 1100122 * @date 2019年3月22日 下午7:55:55 * @param cardNum * @return * @throws */ public static String bankCard(String cardNum) { if (StringUtils.isBlank(cardNum)) { return ""; } return StringUtils.left(cardNum, 6).concat(StringUtils.removeStart(StringUtils.leftPad(StringUtils.right(cardNum, 4), StringUtils.length(cardNum), "*"), "******")); } /** * * @Title: desensitizeEmail * @Description:[电子邮箱] 邮箱前缀仅显示第一个字母,前缀其余隐藏,用星号代替,@及后面的地址显示<例子:g**@163.com> * @author 1100122 * @date 2019年3月22日 下午7:51:29 * @param email * @return * @throws */ public static String desensitizeEmail(String email) { if (StringUtils.isBlank(email)) { return ""; } int index = StringUtils.indexOf(email, "@"); if (index <= 1) { return email; } else { return StringUtils.rightPad(StringUtils.left(email, 1), index, "*").concat(StringUtils.mid(email, index, StringUtils.length(email))); } } /** * * @Title: desensitizeName * @Description: [中文姓名] 只显示第一个汉字,其余隐藏为2个星号<例子:李**> * @author 1100122 * @date 2019年3月22日 下午7:51:37 * @param fullName * @return * @throws */ private static final Object desensitizeName(String fullName) { if (StringUtils.isBlank(fullName)) { return ""; } String name = StringUtils.left(fullName, 1); return StringUtils.rightPad(name, StringUtils.length(fullName), "*"); }
/** * * @Title: toJsonString * @Description: 日志输出 * @author shiliang.feng * @date 2019年8月16日 下午2:25:10 * @param object * @return */ public static String toJsonString(Object object) { return JSON.toJSONString(object, getValueFilter()); }
/** * * @Title: getValueFilter * @Description: 日志脱敏主方法 * @author shiliang.feng * @date 2019年8月16日 下午2:25:28 * @return */ private static final ValueFilter getValueFilter() { return (Object obj, String key, Object value) -> { try { SensitiveAnn annotation = obj.getClass().getDeclaredField(key).getAnnotation(SensitiveAnn.class); if (null != annotation && value instanceof String) { String strVal = (String) value; if (StringUtils.isNotBlank(strVal)) { switch (annotation.type()) { case PHONE: return mobilePhone(strVal); case ID_CARD: return idCardNum(strVal); case BANK_CARD: return bankCard(strVal); case NAME: return desensitizeName(strVal); case EMAIL: return desensitizeEmail(strVal); default: break; } } } } catch (NoSuchFieldException | SecurityException e) { } return value; }; }
public static void main(String[] args) { CardInfo cardInfo = new CardInfo(); cardInfo.setCardId("6228480402564890018"); cardInfo.setName("冯小明"); cardInfo.setPhone("18699999999"); cardInfo.setBank("463553564656545646"); System.out.println(SensitiveInfoUtils.toJsonString(cardInfo)); System.out.println(JSON.toJSONString(cardInfo)); }