verify.js 2.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. import areaSet from './area'
  2. /**
  3. * @description 校验出生日期
  4. * @param {String} birth 8位出生日期 形如20210601
  5. * @returns {Boolean} 校验是否通过
  6. */
  7. const verifyBirthDate = (birth) => {
  8. // 格式化传入的日期格式为 yyyy-mm-dd
  9. const serializedBirth = `${birth.slice(0, 4)}-${birth.slice(4, 6)}-${birth.slice(6)}`;
  10. const birthDate = new Date(serializedBirth).getTime();
  11. // 如果日期格式无效,形如 2020-13-14、2021-02-29 等,则返回 false
  12. // 无效的日期格式,Date.prototype.getTime() 会返回 NaN
  13. if (Number.isNaN(birthDate)) return false;
  14. // 如果传入的日期领先于当前日期,比如传入 20990102 则返回 false
  15. if (birthDate > new Date().getTime()) return false;
  16. // 否则返回 true,检验通过
  17. return true;
  18. };
  19. /**
  20. * @description 校验码字符校验函数
  21. * @param {String} cardNum 传入的身份证号
  22. * @returns {Boolean} 校验是否通过
  23. */
  24. const verifyCheckCode = (cardNum) => {
  25. // 本体码
  26. const masterCode = cardNum.slice(0, 17).split("");
  27. // 校验码
  28. const checkCode = cardNum.slice(17).toLocaleLowerCase();
  29. // 校验因子
  30. const weightingFactor = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2];
  31. // 校验码换算关系
  32. const pattern = {0: 1, 1: 0, 2: "x", 3: 9, 4: 8, 5: 7, 6: 6, 7: 5, 8: 4, 9: 3, 10: 2};
  33. // 各位值与对应校验因子相乘,并求和
  34. const sum = masterCode.reduce((pre, cur, ix) => pre + cur * weightingFactor[ix], 0);
  35. // 累加值对11取余
  36. const val = sum % 11;
  37. // 能与换算关系对应上则返回true,否则返回false
  38. return pattern[val] === checkCode;
  39. };
  40. /**
  41. * @description 身份证号码校验,判断输入的身份证号码是否合法
  42. * @param {String} cardNum 待校验身份证号码
  43. * @returns {Boolean} 是否校验通过
  44. */
  45. export const verifyCardNum = (cardNum = "") => {
  46. // 对参数进行格式化
  47. const serializedCardNum = cardNum.toString().trim();
  48. // 长度校验
  49. if (serializedCardNum.length !== 18) return false;
  50. // 简单的正则校验
  51. if (!/^[1-9]\d{5}(18|19|[2-9]\d)\d{9}[0-9Xx]$/.test(serializedCardNum)) {
  52. return false;
  53. }
  54. // 地址码检验
  55. const areaCode = Number(serializedCardNum.slice(0, 6));
  56. if (areaSet.indexOf(areaCode) === -1) return false;
  57. // 出生日期码校验
  58. const birthCode = serializedCardNum.slice(6, 14);
  59. if (!verifyBirthDate(birthCode)) return false;
  60. // 校验码校验,(有bug,暂时不用)
  61. //if (!verifyCheckCode(serializedCardNum)) return false;
  62. // 所有校验通过后,返回true
  63. return true;
  64. };