壹、身份证18位数字代表含义 😄😄
要对身份证进行处理,前提就得先了解身份证含义。2013年1月1日起第一代居民身份证将停止使用,全面使用第二代居民身份证。所以就不考虑15位的情况。
1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
省份 | 所在城市 | 区县代码 | 出生日期 | 所在派出所代码 | 性别 | 校验码 |
贰、身份证合法性校验 😆😆
现在知道身份证18位数字的含义以后,接着就可以对其进行精准校验。也就是从省份开始校验、其次所在城市以及区县、接着出生日期、最后到校验码。下面上完整的代码,代码中该有的注释全都有。
注:前端的话只能做一些常规的校验,比如这个身份证通过校验,但是真实的存不存在,以及名字匹配等等还得搭配着实名认证接口进行。
index.vue ✏️ ✏️ ✏️ ✏️
<template>
<div style="padding: 20px;width: 60%;">
<div style="display: flex;align-items: center;">
<span>校验身份证件是否有效:</span>
<el-input style="width: 300px;margin: 0 20px;" v-model="idCard"/>
<el-button @Click="onCheck">校验</el-button>
</div>
<div>
<span>校验结果:</span>
<span style="margin-left: 20px;">{{ result }}</span>
</div>
<div>
<el-button @Click="getUserInfo">根据身份证获取信息</el-button>
</div>
</div>
</template>
<script lang="ts">
import IdCardValid from '@/utils/IdCardValid'
export default defineComponent({
setup() {
const idCard = ref<string>('')
const result = ref<string>('')
const onCheck = () => {
result.value = IdCardValid._overallValid(idCard.value) ? '通过' : '身份证号不合法'
}
const getUserInfo = () => {
console.log(IdCardValid._getInfo(idCard.value))
}
return {
idCard,
result,
onCheck,
getUserInfo,
}
}
})
</script>
utils/IdCardValid.ts ✏️ ✏️ ✏️ ✏️
import areaCodes from './areaCodes.json'
interface IdCardValidEvent {
_emptyAndLength: (idCard: string) => boolean
_idCardRule: (idCard: string) => boolean
_checkProvince: (idCard: string,result: string[]) => boolean | string
_checkCity: (idCard: string,result: string[]) => boolean | string
_checkBirthday: (idCard: string,result: string[]) => boolean
_overallValid: (idCard: string,result: string[]) => boolean
_getInfo: (idCard: string) => string[]
}
export class IdCardValidFun implements IdCardValidEvent{
// 第一步 进行非空以及长度校验
_emptyAndLength(idCard: string) {
return !!(idCard && idCard.length === 18);
}
// 第二步 进行身份证号规则校验
// 身份证号是由18位数字或17位数字+x组成
_idCardRule(idCard: string) {
const reg = /(^\d{17}(\d|X)$)/;
return reg.test(idCard)
}
// 第三步 验证省份
_checkProvince(idCard: string,result: string[] = []) {
// 这里是省份的代码,可自行百度查询
const provinceCity: {
[key: number]: string
} = {
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: '澳门特别行政区'
}
const province: number = parseInt(idCard.substring(0, 2))
result.push(provinceCity[province])
return !!provinceCity[province]
}
// 第四步 验证城市以及区县代码 这里的JSON我是在网上下载的,可能还有的代码是一代.
_checkCity(idCard: string,result: string[] = []) {
const areaCodesObj: {
[key: number]: string
} = areaCodes
const city: number = parseInt(idCard.substring(0, 6))
result.push(areaCodesObj[city])
return !!areaCodesObj[city]
}
// 第五步 出生日期校验
_checkBirthday(idCard: string,result: string[] = []) {
const idCardReg = /^(\d{6})(\d{4})(\d{2})(\d{2})(\d{3})([0-9]|X)$/
const arrData:string[] = idCard.match(idCardReg)!
const year:number = parseInt(arrData[2])
const month:number = parseInt(arrData[3])
const day:number = parseInt(arrData[4])
const birthday = new Date(year + '/' + month + '/' + day);
// 日期不合法直接不通过校验
if (birthday.getMonth() != 0 && (!birthday.getMonth() || !birthday.getDay())) {
return false
}
result.push(year + '-' + month + '-' + day)
const currentData = new Date()
const currentYear = currentData.getFullYear()
const age = currentYear - year
// 不知道现在小宝宝多久上户口,所以我这里写的是年龄大于0岁的 1岁到200岁之间有效
return (age > 0 && age <= 200)
}
// 所在地派出所的代码就不验证了 实在太多了
// 第十七位也没什么好校验的 就一个数字 奇数是男性,偶数是女性
// 第七步 校验最后一位校验码
// 这里自行百度身份证最后一位的计算方法(固定算法)
_checkCode(idCard: string) {
const factorArray = [7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10, 5, 8, 4, 2]
// 对应的最后一位身份证的号码
const correspondArray = ['1', '0', 'X', '9', '8', '7', '6', '5', '4', '3', '2']
let cardTemp:number = 0
for (let i = 0; i < 17; i++) {
cardTemp += parseInt(idCard.substring(i, i + 1)) * factorArray[i];
}
return correspondArray[cardTemp % 11] === idCard.substring(17, 18)
}
_overallValid(idCard: string) {
// 1 这里如果为空或者没有18位直接返回false
if (!this._emptyAndLength(idCard)) {
return false
}
// 2
if (!this._idCardRule(idCard)) {
return false
}
// 3
if (!this._checkProvince(idCard)) {
return false
}
// 4
if (!this._checkCity(idCard)) {
return false
}
// 5
if (!this._checkBirthday(idCard)) {
return false
}
// 6
return this._checkCode(idCard);
}
_getInfo(idCard: string) {
let result:string[] = []
if (!this._emptyAndLength(idCard)) {
return []
}
if (!this._idCardRule(idCard)) {
return []
}
if (!this._checkProvince(idCard, result)) {
return []
}
if (!this._checkCity(idCard, result)) {
return []
}
if (!this._checkBirthday(idCard, result)) {
return []
}
if (!this._checkCode(idCard)) {
return []
}
result.push(parseInt(idCard.substring(17, 18)!) % 2 == 0 ? '0' : '1')
return result
}
}
const IdCardValid = new IdCardValidFun()
export default IdCardValid
utils/areaCodes.json ✏️ ✏️ ✏️ ✏️
这个json文件主要是存放的省市县的区县代码,文件比较大,可自行百度下载,也可以联系我免费提供。也可以不校验所在城市和区县。需要联系我👉👉 SH--TS。
utils/images.d.ts ✏️ ✏️ ✏️ ✏️
declare module '*.json'
效果图
合法
不合法
叁 、提取省市县、出生日期、性别 😊😊
代码中已经放入提取的方法。返回一个数组
效果
肆、脱敏 😃😃
我是Etc.End。如果文章对你有所帮助,能否帮我点个免费的赞和收藏😍。
👇 👇 👇 👇 👇 👇 👇 👇 👇 👇 👇 👇