package com.ruoyi.im.util; import java.util.regex.Pattern; import java.util.Calendar; import java.util.HashMap; import java.util.Map; public class ValidatorUtil { // 手机号正则表达式(匹配中国大陆手机号) private static final String PHONE_REGEX = "^1[3-9]\\d{9}$"; // 身份证号正则表达式(18位) private static final String ID_CARD_REGEX = "^[1-9]\\d{5}(18|19|20)\\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|10|20|30|31)\\d{3}[0-9Xx]$"; // 省份代码映射 private static final Map PROVINCE_CODES = new HashMap<>(); static { // 初始化省份代码 PROVINCE_CODES.put("11", "北京"); PROVINCE_CODES.put("12", "天津"); PROVINCE_CODES.put("13", "河北"); PROVINCE_CODES.put("14", "山西"); PROVINCE_CODES.put("15", "内蒙古"); PROVINCE_CODES.put("21", "辽宁"); PROVINCE_CODES.put("22", "吉林"); PROVINCE_CODES.put("23", "黑龙江"); PROVINCE_CODES.put("31", "上海"); PROVINCE_CODES.put("32", "江苏"); PROVINCE_CODES.put("33", "浙江"); PROVINCE_CODES.put("34", "安徽"); PROVINCE_CODES.put("35", "福建"); PROVINCE_CODES.put("36", "江西"); PROVINCE_CODES.put("37", "山东"); PROVINCE_CODES.put("41", "河南"); PROVINCE_CODES.put("42", "湖北"); PROVINCE_CODES.put("43", "湖南"); PROVINCE_CODES.put("44", "广东"); PROVINCE_CODES.put("45", "广西"); PROVINCE_CODES.put("46", "海南"); PROVINCE_CODES.put("50", "重庆"); PROVINCE_CODES.put("51", "四川"); PROVINCE_CODES.put("52", "贵州"); PROVINCE_CODES.put("53", "云南"); PROVINCE_CODES.put("54", "西藏"); PROVINCE_CODES.put("61", "陕西"); PROVINCE_CODES.put("62", "甘肃"); PROVINCE_CODES.put("63", "青海"); PROVINCE_CODES.put("64", "宁夏"); PROVINCE_CODES.put("65", "新疆"); PROVINCE_CODES.put("71", "台湾"); PROVINCE_CODES.put("81", "香港"); PROVINCE_CODES.put("82", "澳门"); } // 身份证校验码权重 private static final int[] ID_CARD_WEIGHT = {7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2}; // 身份证校验码对应值 private static final char[] ID_CARD_CHECK_CODE = {'1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2'}; /** * 验证手机号格式 * @param phone 手机号码 * @return 是否有效 */ public static boolean isValidPhone(String phone) { if (phone == null || phone.trim().isEmpty()) { return false; } // 移除可能的分隔符(如空格、短横线等) String cleanedPhone = phone.replaceAll("[\\s-]+", ""); return Pattern.matches(PHONE_REGEX, cleanedPhone); } /** * 验证身份证号格式 * @param idCard 身份证号码 * @return 是否有效 */ public static boolean isValidIdCard(String idCard) { if (idCard == null || idCard.trim().isEmpty()) { return false; } // 转换为大写以便统一处理 String cleanedIdCard = idCard.trim().toUpperCase(); // 基本格式校验 if (!Pattern.matches(ID_CARD_REGEX, cleanedIdCard)) { return false; } // 校验省份代码 String provinceCode = cleanedIdCard.substring(0, 2); if (!PROVINCE_CODES.containsKey(provinceCode)) { return false; } // 校验生日日期 if (!isValidBirthday(cleanedIdCard.substring(6, 14))) { return false; } // 校验校验码 return isValidCheckCode(cleanedIdCard); } /** * 验证身份证中的生日日期是否有效 * @param birthdayStr 生日字符串(YYYYMMDD格式) * @return 是否有效 */ private static boolean isValidBirthday(String birthdayStr) { try { int year = Integer.parseInt(birthdayStr.substring(0, 4)); int month = Integer.parseInt(birthdayStr.substring(4, 6)); int day = Integer.parseInt(birthdayStr.substring(6, 8)); // 检查年份范围(假设身份证持有者年龄在0-150岁之间) int currentYear = Calendar.getInstance().get(Calendar.YEAR); if (year < currentYear - 150 || year > currentYear) { return false; } // 检查月份 if (month < 1 || month > 12) { return false; } // 检查日期 if (day < 1 || day > 31) { return false; } // 检查特定月份的天数 if ((month == 4 || month == 6 || month == 9 || month == 11) && day > 30) { return false; } // 检查闰年二月 if (month == 2) { boolean isLeapYear = (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0); if (isLeapYear && day > 29) { return false; } if (!isLeapYear && day > 28) { return false; } } return true; } catch (NumberFormatException e) { return false; } } /** * 验证身份证校验码 * @param idCard 身份证号码 * @return 校验码是否正确 */ private static boolean isValidCheckCode(String idCard) { try { int sum = 0; for (int i = 0; i < 17; i++) { int digit = Character.getNumericValue(idCard.charAt(i)); sum += digit * ID_CARD_WEIGHT[i]; } int mod = sum % 11; char checkCode = ID_CARD_CHECK_CODE[mod]; return checkCode == idCard.charAt(17); } catch (Exception e) { return false; } } /** * 测试方法 */ public static void main(String[] args) { // 测试手机号验证 String[] testPhones = { "13800138000", "12345678901", "1861234567", "19612345678", " 138-0013-8000 ", "123abc45678" }; System.out.println("手机号验证测试:"); for (String phone : testPhones) { System.out.println(phone + " : " + isValidPhone(phone)); } System.out.println("\n身份证验证测试:"); // 测试身份证验证 String[] testIdCards = { "11010519491231002X", // 有效身份证 "123456789012345678", // 无效身份证 "110105194902300021", // 无效日期(非闰年2月30日) "110105194913310022", // 无效月份 "999999200001010000" // 无效省份代码 }; for (String idCard : testIdCards) { System.out.println(idCard + " : " + isValidIdCard(idCard)); } } }