發表到這裡,除了Day 1,每一篇幾乎與資安弱掃扯上關係,隱碼也不例外,不能外洩個資,舉凡身份證號、手機號碼、姓名、信用卡號、E-Mail和生日都算,也因此寫出隱碼公用程式,提供兩個Method。
import java.util.Arrays;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class SensitivityUtil {
public enum SensitivityType {
ID,
PHONE,
CNAME,
CREDIT_CARD,
EMAIL,
BIRTHDAY
}
public static String hiddenCode (SensitivityType stype, String orig) {
if (orig == null || orig.length() < 2) return orig;
switch(stype) {
case ID: // 身份證號
return orig.substring(0, 2) + new String(new char[orig.length() - 4]).replace("\0", "*") + orig.substring(orig.length() - 2);
case PHONE: // 手機、電話
return orig.matches("^\\+\\d{4,}") ? orig.replaceAll("(?<=[^#-]\\d{7})\\d", "*") : orig.replaceAll("(?<=[^#-]\\d{4})\\d", "*");
case CNAME: // 中文姓名
if (orig.length() == 2) {
return orig.substring(0, 1) + "〇" + orig.substring(orig.length() - 1);
}
return orig.substring(0, 1) + new String(new char[orig.length() - 2]).replace("\0", "〇") + orig.substring(orig.length() - 1);
case CREDIT_CARD: // 信用卡號
return orig.substring(0, 4) + new String(new char[orig.length() - 8]).replace("\0", "X") + orig.substring(orig.length() - 4);
case EMAIL: // 電子郵件
return orig.replaceAll("(?<=.{3}).(?=[^@]*?@)", "*");
case BIRTHDAY: // 生日
return orig.replaceFirst("(\\d{2})\\d{2}", "$1**").replaceFirst("\\d{2}$", "**");
}
return orig;
}
public String hiddenByJSON(String orig, Map<String, SensitivityType> hidMap) {
if (orig == null || orig.length() < 2) return orig;
for (Map.Entry<String, SensitivityType> entry : hidMap.entrySet()) {
String keyName = entry.getKey();
SensitivityType sType = entry.getValue();
String origPat = "\"" + keyName + "\":\"(.+?)\"";
Pattern pat = Pattern.compile(origPat);
Matcher mat = pat.matcher(orig);
if (mat.find()) {
String hidCode = hiddenCode(sType, mat.group(1));
orig = orig.replaceFirst(origPat, "\"" + keyName + "\":\"" + hidCode + "\"");
}
}
return orig;
}
public static void main(String[] args) {
System.out.println(SensitivityUtil.hiddenCode(SensitivityUtil.SensitivityType.CNAME, "鐵人賽"));
System.out.println(SensitivityUtil.hiddenCode(SensitivityUtil.SensitivityType.CNAME, "張菲"));
System.out.println(SensitivityUtil.hiddenCode(SensitivityUtil.SensitivityType.CNAME, "谷辣斯.尤達卡"));
System.out.println(SensitivityUtil.hiddenCode(SensitivityUtil.SensitivityType.CREDIT_CARD, "5130123456783666"));
System.out.println(SensitivityUtil.hiddenCode(SensitivityUtil.SensitivityType.EMAIL, "tsaijemmy@google.com"));
System.out.println(SensitivityUtil.hiddenCode(SensitivityUtil.SensitivityType.BIRTHDAY, "1970-01-01"));
SensitivityUtil util = new SensitivityUtil();
Map<String, SensitivityType> hidMap = new HashMap<String, SensitivityType>();
hidMap.put("CustID", SensitivityUtil.SensitivityType.ID);
hidMap.put("PhoneNumber", SensitivityUtil.SensitivityType.PHONE);
String orig = "{\"header\":{\"InputClass\":\"com.company.biz.LoginVO\",\"TxnCode\":\"BIZ000\",\"StampTime\":true,\"TXN_DATA\":{},\"CustID\":\"A123456789\",\"PhoneNumber\":\"0932123456\",\"Browser\":{\"chrome\":\"100.0.4896.127\"}},\"body\":{\"pageCount\":10}}";
System.out.println(util.hiddenByJSON(orig, hidMap));
String[] strPhoneNumbers = {
"0912345678",
"02-77123456",
"+886912345678",
"(02)77123456",
"(02)77123456#12345",
"02-77123456-12345",
};
for(String phoneNumber : strPhoneNumbers) {
String maxNum = Arrays.asList(phoneNumber.split("\\D")).stream().max(Comparator.comparingInt(String::length)).get();
int cnt = (int) maxNum.chars().filter(Character::isDigit).count();
System.out.println( phoneNumber + " : " + SensitivityUtil.hiddenCode(SensitivityUtil.SensitivityType.PHONE, phoneNumber));
}
}
}
從java main測試得到的結果如下:
鐵〇賽
張〇菲
谷〇〇〇〇〇卡
5130XXXXXXXX3666
tsa******@google.com
19**-01-**
{"header":{"InputClass":"com.company.biz.LoginVO","TxnCode":"BIZ000","StampTime":true,"TXN_DATA":{},"CustID":"A1******89","PhoneNumber":"09321*****","Browser":{"chrome":"100.0.4896.127"}},"body":{"pageCount":10}}
0912345678 : 09123*****
02-77123456 : 02-77123***
+886912345678 : +8869123*****
(02)77123456 : (02)7712****
(02)77123456#12345 : (02)7712****#12345
02-77123456-12345 : 02-77123***-12345