我们知道涉及到借贷、信用卡申请类似的项目都用户的身份信息都是比较敏感的,所以经常要去验证用户的身份信息,其中身份证的信息验证是比较麻烦的,所以自己也整理了一份相关的校验方式供大家参考。
一、省份
每个省都有对应的编号:
const city = {
11: "北京",
12: "天津",
13: "河北",
14: "山西",
15: "内蒙古",
21: "辽宁",
22: "吉林",
23: "黑龙江 ",
31: "上海",
32: "江苏",
33: "浙江",
34: "安徽",
35: "福建",
36: "江西",
37: "山东",
41: "河南",
42: "湖北 ",
43: "湖南",
44: "广东",
45: "广西",
46: "海南",
50: "重庆",
51: "四川",
52: "贵州",
53: "云南",
54: "西藏 ",
61: "陕西",
62: "甘肃",
63: "青海",
64: "宁夏",
65: "新疆",
71: "台湾",
81: "香港",
82: "澳门",
91: "国外 "
};
二、生日
这里只考虑18位的身份证,15位一代身份证暂不列入考虑范围:
const validBirthday = idcard => {
//身份证18位时,次序为省(3位)市(3位)年(4位)月(2位)日(2位)校验位(4位),校验位末尾可能为X
let re_eighteen = /^(\d{6})(\d{4})(\d{2})(\d{2})(\d{3})([0-9]|X|x|\*)$/i;
let arr_data = idcard.match(re_eighteen);
let year = arr_data[2];
let month = arr_data[3];
let day = arr_data[4];
let birthday = new Date(year + '/' + month + '/' + day);
return validDate(year, month, day, birthday);
return false;
}
三、日期
日期的合法性是通过生日来推算:
const validDate = (year, month, day, birthday) => {
let now = new Date();
let now_year = now.getFullYear();
//年月日是否合理
if (birthday.getFullYear() == year && (birthday.getMonth() + 1) == month && birthday.getDate() == day) {
//判断年份的范围(0岁到100岁之间)
let time = now_year - year;
if (time >= 0 && time <= 100) {
return true;
}
return false;
}
return false;
}
最后整合成完整的身份证校验:
const validIDcard = idcard => {
idcard = idcard.replace(/\*/g, 'X');
idcard = idcard.replace(/x/g, 'X');
let pass = true;
let checkReg = null;
let carid_check = /(^\d{18}$)|(^\d{17}(\d|X|x|\*)$)/i;
if (!idcard || !carid_check.test(idcard)) { //基本长度,格式校验
pass = false;
} else if (!city[idcard.substr(0, 2)]) { //省份校验
pass = false;
} else if (!validBirthday(idcard)) {
pass = false;
} else {
if (parseInt(idcard.substr(6, 4) % 4 == 0 || (parseInt(idcard.substr(6, 4)) % 100 == 0 && parseInt(idcard.substr(6, 4)) % 4 == 0))) {
checkReg = /^[1-9][0-9]{5}19[0-9]{2}((01|03|05|07|08|10|12)(0[1-9]|[1-2][0-9]|3[0-1])|(04|06|09|11)(0[1-9]|[1-2][0-9]|30)|02(0[1-9]|[1-2][0-9]))[0-9]{3}[0-9Xx*]$/i; //闰年出生日期的合法性正则表达式
} else {
checkReg = /^[1-9][0-9]{5}19[0-9]{2}((01|03|05|07|08|10|12)(0[1-9]|[1-2][0-9]|3[0-1])|(04|06|09|11)(0[1-9]|[1-2][0-9]|30)|02(0[1-9]|1[0-9]|2[0-8]))[0-9]{3}[0-9Xx*]$/i; //平年出生日期的合法性正则表达式
}
//18位身份证需要验证最后一位校验位
if (checkReg.test(idcard)) {
idcard = idcard.split('');
//∑(ai×Wi)(mod 11)
//加权因子
let factor = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2];
//校验位
let parity = [1, 0, 'X', 9, 8, 7, 6, 5, 4, 3, 2];
let sum = 0;
let ai = 0;
let wi = 0;
for (let i = 0; i < 17; i++) {
ai = idcard[i];
wi = factor[i];
sum += ai * wi;
}
let last = parity[sum % 11];
if (parity[sum % 11] != idcard[17]) {
pass = false;
}
}
}
return pass;
}
现在直接调用validIDcard
传入你的身份证试试吧。
网友评论