外國人永居居留證的證號(hào)校驗(yàn)

根據(jù)國人身份證校驗(yàn)規(guī)則調(diào)整外國人身份證校驗(yàn)

根據(jù)國家移民管理局公布的新版外國人永久居留身份證適配性改造要點(diǎn)。核心點(diǎn)如果下圖:

1.jpg

你會(huì)發(fā)現(xiàn)18位身份證,我們的身份證和外國人永居證的差別只是前6位的校驗(yàn)不同。

  • 身份證校驗(yàn)規(guī)則:
//身份證
            function checkSFZ(_sfz) {
                var vcity = {
                    11: "北京",
                    12: "天津",
                    13: "河北",
                    14: "山西",
                    15: "內(nèi)蒙古",
                    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: "新疆",
                    83: "臺(tái)灣",//行政區(qū)劃71,身份證是83
                    81: "香港",
                    82: "澳門",
                    91: "國外"
                };

                // 檢查號(hào)碼是否符合規(guī)范,包括長度,類型
                var isCardNo = function (card) {
                    // 身份證號(hào)碼為15位或者18位,15位時(shí)全為數(shù)字,18位前17位為數(shù)字,最后一位是校驗(yàn)位,可能為數(shù)字或字符X
                    var reg = /(^\d{15}$)|(^\d{17}(\d|X)$)/;
                    if (reg.test(card) === false) {
                        return false;
                    }
                    return true;
                };

                // 取身份證前兩位,校驗(yàn)省份
                var checkProvince = function (card) {
                    var province = card.substr(0, 2);
                    if (vcity[province] == undefined) {
                        return false;
                    }
                    return true;
                };

                // 檢查生日是否正確
                var checkBirthday = function (card) {
                    var len = card.length;
                    // 身份證15位時(shí),次序?yàn)槭。?位)市(3位)年(2位)月(2位)日(2位)校驗(yàn)位(3位),皆為數(shù)字
                    if (len == '15') {
                        var re_fifteen = /^(\d{6})(\d{2})(\d{2})(\d{2})(\d{3})$/;
                        var arr_data = card.match(re_fifteen);
                        var year = arr_data[2];
                        var month = arr_data[3];
                        var day = arr_data[4];
                        var birthday = new Date('19' + year + '/' + month + '/' + day);
                        return verifyBirthday('19' + year, month, day, birthday);
                    }
                    // 身份證18位時(shí),次序?yàn)槭。?位)市(3位)年(4位)月(2位)日(2位)校驗(yàn)位(4位),校驗(yàn)位末尾可能為X
                    if (len == '18') {
                        var re_eighteen = /^(\d{6})(\d{4})(\d{2})(\d{2})(\d{3})([0-9]|X)$/;
                        var arr_data = card.match(re_eighteen);
                        var year = arr_data[2];
                        var month = arr_data[3];
                        var day = arr_data[4];
                        var birthday = new Date(year + '/' + month + '/' + day);
                        return verifyBirthday(year, month, day, birthday);
                    }
                    return false;
                };

                // 校驗(yàn)日期
                var verifyBirthday = function (year, month, day, birthday) {
                    var now = new Date();
                    var now_year = now.getFullYear();
                    // 年月日是否合理
                    if (birthday.getFullYear() == year
                        && (birthday.getMonth() + 1) == month
                        && birthday.getDate() == day) {
                        // 判斷年份的范圍(3歲到100歲之間)
                        var time = now_year - year;
                        if (time <= 120) {
                            return true;
                        }
                        return false;
                    }
                    return false;
                };

                // 校驗(yàn)位的檢測(cè)
                var checkParity = function (card) {
                    // 15位轉(zhuǎn)18位
                    card = changeFivteenToEighteen(card);
                    var len = card.length;
                    if (len == '18') {
                        var arrInt = new Array(7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10,
                            5, 8, 4, 2);
                        var arrCh = new Array('1', '0', 'X', '9', '8', '7', '6', '5',
                            '4', '3', '2');
                        var cardTemp = 0, i, valnum;
                        for (i = 0; i < 17; i++) {
                            cardTemp += card.substr(i, 1) * arrInt[i];
                        }
                        valnum = arrCh[cardTemp % 11];
                        if (valnum == card.substr(17, 1)) {
                            return true;
                        }
                        return false;
                    }
                    return false;
                };

                // 15位轉(zhuǎn)18位身份證號(hào)
                var changeFivteenToEighteen = function (card) {
                    if (card.length == '15') {
                        var arrInt = new Array(7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10,
                            5, 8, 4, 2);
                        var arrCh = new Array('1', '0', 'X', '9', '8', '7', '6', '5',
                            '4', '3', '2');
                        var cardTemp = 0, i;
                        card = card.substr(0, 6) + '19'
                            + card.substr(6, card.length - 6);
                        for (i = 0; i < 17; i++) {
                            cardTemp += card.substr(i, 1) * arrInt[i];
                        }
                        card += arrCh[cardTemp % 11];
                        return card;
                    }
                    return card;
                };

                var checkCode = function (_sfz) {
                    // 是否為空
                    if (_sfz === '') {
                        // alert('請(qǐng)輸入身份證號(hào),身份證號(hào)不能為空');
                        return false;
                    }
                    // 校驗(yàn)長度,類型
                    if (isCardNo(_sfz) === false) {
                        // alert('您輸入的身份證號(hào)碼不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    // 檢查省份
                    if (checkProvince(_sfz) === false) {
                        // alert('您輸入的身份證號(hào)碼不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    // 校驗(yàn)生日
                    if (checkBirthday(_sfz) === false) {
                        // alert('您輸入的身份證號(hào)碼生日不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    // 檢驗(yàn)位的檢測(cè)
                    if (checkParity(_sfz) === false) {
                        // alert('您的身份證校驗(yàn)位不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    return true;
                }

                return checkCode(_sfz);
            }
            
  • 外國人永居證校驗(yàn)規(guī)則:
//外國人身份證(新版永居證證件號(hào)碼18位)
            function checkOutSFZ(_sfz) {
                //參考移民管理局的文檔:https://www.nia.gov.cn/20231013/2.pdf
                //格式:9(身份標(biāo)識(shí)碼) 32(受理地代碼) 682(國家和地區(qū)代碼) 19850101(出生日期) 001(順序碼) 7(校驗(yàn)碼)。
                var vcity = {
                    11: "北京",
                    12: "天津",
                    13: "河北",
                    14: "山西",
                    15: "內(nèi)蒙古",
                    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: "新疆",
                    83: "臺(tái)灣",//行政區(qū)劃71,身份證是83
                    81: "香港",
                    82: "澳門",
                    91: "國外"
                };

                // 檢查號(hào)碼是否符合規(guī)范,包括長度,類型
                var isCardNo = function (card) {
                    //18位前17位為數(shù)字,最后一位是校驗(yàn)位,可能為數(shù)字或字符X
                    var reg = /(^\d{17}(\d|X)$)/;
                    if (reg.test(card) === false) {
                        return false;
                    }
                    return true;
                };

                // 取身份證前1位,校驗(yàn)身份標(biāo)識(shí),1-8位國內(nèi)人士,9為外國人。
                var personMark = function (card){
                    var mark = card.substring(0,1);
                    return mark==9;//是外國人
                };

                // 取身份證前2,3位,校驗(yàn)省份
                var checkProvince = function (card) {
                    var province = card.substring(1,3);
                    if (vcity[province] == undefined) {
                        return false;
                    }
                    return true;
                };

                // 檢查生日是否正確
                var checkBirthday = function (card) {
                    var len = card.length;
                    // 身份證15位時(shí),次序?yàn)槭。?位)市(3位)年(2位)月(2位)日(2位)校驗(yàn)位(3位),皆為數(shù)字
                    if (len == '15') {
                        var re_fifteen = /^(\d{6})(\d{2})(\d{2})(\d{2})(\d{3})$/;
                        var arr_data = card.match(re_fifteen);
                        var year = arr_data[2];
                        var month = arr_data[3];
                        var day = arr_data[4];
                        var birthday = new Date('19' + year + '/' + month + '/' + day);
                        return verifyBirthday('19' + year, month, day, birthday);
                    }
                    // 身份證18位時(shí),次序?yàn)槭。?位)市(3位)年(4位)月(2位)日(2位)校驗(yàn)位(4位),校驗(yàn)位末尾可能為X
                    if (len == '18') {
                        var re_eighteen = /^(\d{6})(\d{4})(\d{2})(\d{2})(\d{3})([0-9]|X)$/;
                        var arr_data = card.match(re_eighteen);
                        var year = arr_data[2];
                        var month = arr_data[3];
                        var day = arr_data[4];
                        var birthday = new Date(year + '/' + month + '/' + day);
                        return verifyBirthday(year, month, day, birthday);
                    }
                    return false;
                };

                // 校驗(yàn)日期
                var verifyBirthday = function (year, month, day, birthday) {
                    var now = new Date();
                    var now_year = now.getFullYear();
                    // 年月日是否合理
                    if (birthday.getFullYear() == year
                        && (birthday.getMonth() + 1) == month
                        && birthday.getDate() == day) {
                        // 判斷年份的范圍(3歲到100歲之間)
                        var time = now_year - year;
                        if (time <= 120) {
                            return true;
                        }
                        return false;
                    }
                    return false;
                };

                // 校驗(yàn)位的檢測(cè)
                var checkParity = function (card) {
                    // 15位轉(zhuǎn)18位
                    card = changeFivteenToEighteen(card);
                    var len = card.length;
                    if (len == '18') {
                        var arrInt = new Array(7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10,
                            5, 8, 4, 2);
                        var arrCh = new Array('1', '0', 'X', '9', '8', '7', '6', '5',
                            '4', '3', '2');
                        var cardTemp = 0, i, valnum;
                        for (i = 0; i < 17; i++) {
                            cardTemp += card.substr(i, 1) * arrInt[i];
                        }
                        valnum = arrCh[cardTemp % 11];
                        if (valnum == card.substr(17, 1)) {
                            return true;
                        }
                        return false;
                    }
                    return false;
                };

                // 15位轉(zhuǎn)18位身份證號(hào)
                var changeFivteenToEighteen = function (card) {
                    if (card.length == '15') {
                        var arrInt = new Array(7, 9, 10, 5, 8, 4, 2, 1, 6, 3, 7, 9, 10,
                            5, 8, 4, 2);
                        var arrCh = new Array('1', '0', 'X', '9', '8', '7', '6', '5',
                            '4', '3', '2');
                        var cardTemp = 0, i;
                        card = card.substr(0, 6) + '19'
                            + card.substr(6, card.length - 6);
                        for (i = 0; i < 17; i++) {
                            cardTemp += card.substr(i, 1) * arrInt[i];
                        }
                        card += arrCh[cardTemp % 11];
                        return card;
                    }
                    return card;
                };

                var checkCode = function (_sfz) {
                    // 是否為空
                    if (_sfz === '') {
                        // alert('請(qǐng)輸入身份證號(hào),身份證號(hào)不能為空');
                        return false;
                    }
                    // 校驗(yàn)長度,類型
                    if (isCardNo(_sfz) === false) {
                        // alert('您輸入的身份證號(hào)碼不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    // 檢查身份標(biāo)識(shí),國內(nèi)人,還是外國人
                    if (personMark(_sfz) === false) {
                        // alert('您輸入的身份證號(hào)碼不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    if (checkProvince(_sfz) === false) {
                        // alert('您輸入的身份證號(hào)碼不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    // 校驗(yàn)生日
                    if (checkBirthday(_sfz) === false) {
                        // alert('您輸入的身份證號(hào)碼生日不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    // 檢驗(yàn)位的檢測(cè)
                    if (checkParity(_sfz) === false) {
                        // alert('您的身份證校驗(yàn)位不正確,請(qǐng)重新輸入');
                        return false;
                    }
                    return true;
                }

                return checkCode(_sfz);
            }

注:如果你想校驗(yàn)得更詳細(xì),可以把國家代碼校驗(yàn)(證號(hào)的前4-6位,參考全球所有的國家代碼/國家區(qū)號(hào),添加枚舉校驗(yàn)),性別校驗(yàn)(證號(hào)的倒數(shù)第2位,1-男,2-女)加上。甚至2017 版外國人永久居留身份證也能做一些基礎(chǔ)校驗(yàn)。這個(gè)自行添加。

參考

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容