# isUserIdentify.mjs

    import genPm from './genPm.mjs'
    import isestr from './isestr.mjs'

    /**
     * 判斷是否為有效中華民國身份證
     *
     * Unit Test: {@link https://github.com/yuda-lyu/wsemi/blob/master/test/isUserIdentify.test.mjs Github}
     * @memberOf wsemi
     * @param {*} v 輸入任意資料
     * @returns {Promise} 回傳Promise，resolve為空代表有效，reject為錯誤訊息
     * @example
     * need test in browser
     *
     * isUserIdentify('A122471399')
     *     .then(function(){
     *         console.log('then')
     *         //code here
     *     })
     *
     */
    function isUserIdentify(v) {

        let pm = genPm()

        //check
        if (!isestr(v)) {
            pm.reject('身份證字號非有效字串')
            return pm
        }

        //身分證字號長度
        if (v.length !== 10) {
            pm.reject('身份證字號長度非10位')
            return pm
        }

        //身分證字號格式，用正則表示式比對第一個字母是否為英文字母
        if (isNaN(v.substr(1, 9)) || (!/^[A-Z]$/.test(v.substr(0, 1)))) {
            pm.reject('身份證格式錯誤，字首需大寫英文')
            return pm
        }

        //按照轉換後權數的大小進行排序
        let idHeader = 'ABCDEFGHJKLMNPQRSTUVXYWZIO'

        //身分證字號轉換
        v = (idHeader.indexOf(v.substring(0, 1)) + 10) + '' + v.substr(1, 9)

        //開始進行身分證數字的相乘與累加，依照順序乘上1987654321
        let s = parseInt(v.substr(0, 1)) +
            parseInt(v.substr(1, 1)) * 9 +
            parseInt(v.substr(2, 1)) * 8 +
            parseInt(v.substr(3, 1)) * 7 +
            parseInt(v.substr(4, 1)) * 6 +
            parseInt(v.substr(5, 1)) * 5 +
            parseInt(v.substr(6, 1)) * 4 +
            parseInt(v.substr(7, 1)) * 3 +
            parseInt(v.substr(8, 1)) * 2 +
            parseInt(v.substr(9, 1))

        //檢查碼
        let checkNum = parseInt(v.substr(10, 1))

        //模數-總和/模數(10)之餘數若等於第九碼的檢查碼則驗證成功, 若餘數為0檢查碼就是0
        if ((s % 10) === 0 || (10 - s % 10) === checkNum) {
            //有效
        }
        else {
            pm.reject('非有效身份證')
            return pm
        }

        pm.resolve()
        return pm
    }

    export default isUserIdentify