2021-01-11 17:55:24 +08:00
|
|
|
|
package idvalidator
|
2021-01-10 13:29:14 +08:00
|
|
|
|
|
2021-01-10 14:56:35 +08:00
|
|
|
|
import (
|
2021-01-10 19:22:33 +08:00
|
|
|
|
"errors"
|
2021-01-11 11:53:22 +08:00
|
|
|
|
"strconv"
|
2021-01-11 18:48:50 +08:00
|
|
|
|
"time"
|
|
|
|
|
|
2021-01-12 11:36:44 +08:00
|
|
|
|
"github.com/guanguans/id-validator/data"
|
2021-01-10 14:56:35 +08:00
|
|
|
|
)
|
|
|
|
|
|
2021-01-11 18:48:50 +08:00
|
|
|
|
// 身份证信息
|
2021-01-27 11:29:38 +08:00
|
|
|
|
type idInfo struct {
|
2021-01-11 18:48:50 +08:00
|
|
|
|
AddressCode int
|
|
|
|
|
Abandoned int
|
|
|
|
|
Address string
|
|
|
|
|
AddressTree []string
|
|
|
|
|
Birthday time.Time
|
|
|
|
|
Constellation string
|
|
|
|
|
ChineseZodiac string
|
|
|
|
|
Sex int
|
|
|
|
|
Length int
|
2021-01-12 14:18:17 +08:00
|
|
|
|
CheckBit string
|
2021-01-11 18:48:50 +08:00
|
|
|
|
}
|
|
|
|
|
|
2021-01-10 13:29:14 +08:00
|
|
|
|
// 验证身份证号合法性
|
|
|
|
|
func IsValid(id string) bool {
|
2021-01-27 11:29:38 +08:00
|
|
|
|
code, err := generateCode(id)
|
2021-01-11 17:55:24 +08:00
|
|
|
|
if err != nil {
|
2021-01-10 13:29:14 +08:00
|
|
|
|
return false
|
|
|
|
|
}
|
|
|
|
|
|
2021-01-11 17:55:24 +08:00
|
|
|
|
// 检查顺序码、生日码、地址码
|
2021-01-27 11:29:38 +08:00
|
|
|
|
if !checkOrderCode(code["order"]) || !checkBirthdayCode(code["birthdayCode"]) || !checkAddressCode(code["addressCode"], code["birthdayCode"]) {
|
2021-01-10 13:29:14 +08:00
|
|
|
|
return false
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 15位身份证不含校验码
|
|
|
|
|
if code["type"] == "15" {
|
|
|
|
|
return true
|
|
|
|
|
}
|
|
|
|
|
|
2021-01-11 17:55:24 +08:00
|
|
|
|
// 校验码
|
2021-01-27 11:29:38 +08:00
|
|
|
|
return code["checkBit"] == generatorCheckBit(code["body"])
|
2021-01-10 13:29:14 +08:00
|
|
|
|
}
|
2021-01-10 14:56:35 +08:00
|
|
|
|
|
|
|
|
|
// 获取身份证信息
|
2021-01-27 11:29:38 +08:00
|
|
|
|
func GetInfo(id string) (idInfo, error) {
|
2021-01-10 14:56:35 +08:00
|
|
|
|
// 验证有效性
|
|
|
|
|
if !IsValid(id) {
|
2021-01-27 11:29:38 +08:00
|
|
|
|
return idInfo{}, errors.New("Not Valid ID card number.")
|
2021-01-10 14:56:35 +08:00
|
|
|
|
}
|
|
|
|
|
|
2021-01-27 11:29:38 +08:00
|
|
|
|
code, _ := generateCode(id)
|
2021-01-11 18:48:50 +08:00
|
|
|
|
addressCode, _ := strconv.Atoi(code["addressCode"])
|
2021-01-10 14:56:35 +08:00
|
|
|
|
|
2021-01-11 18:48:50 +08:00
|
|
|
|
// 地址信息
|
2021-01-27 11:29:38 +08:00
|
|
|
|
addressInfo := getAddressInfo(code["addressCode"], code["birthdayCode"])
|
2021-01-11 18:48:50 +08:00
|
|
|
|
var addressTree []string
|
|
|
|
|
for _, val := range addressInfo {
|
|
|
|
|
addressTree = append(addressTree, val)
|
2021-01-10 14:56:35 +08:00
|
|
|
|
}
|
|
|
|
|
|
2021-01-11 18:48:50 +08:00
|
|
|
|
// 是否废弃
|
|
|
|
|
var abandoned int
|
|
|
|
|
if data.AddressCode[addressCode] == "" {
|
|
|
|
|
abandoned = 1
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 生日
|
|
|
|
|
birthday, _ := time.Parse("20060102", code["birthdayCode"])
|
|
|
|
|
|
|
|
|
|
// 性别
|
|
|
|
|
sex := 1
|
2021-01-10 14:56:35 +08:00
|
|
|
|
sexCode, _ := strconv.Atoi(code["order"])
|
|
|
|
|
if (sexCode % 2) == 0 {
|
2021-01-11 18:48:50 +08:00
|
|
|
|
sex = 0
|
2021-01-10 14:56:35 +08:00
|
|
|
|
}
|
|
|
|
|
|
2021-01-11 18:48:50 +08:00
|
|
|
|
// 长度
|
|
|
|
|
length, _ := strconv.Atoi(code["type"])
|
|
|
|
|
|
2021-01-27 11:29:38 +08:00
|
|
|
|
return idInfo{
|
2021-01-11 18:48:50 +08:00
|
|
|
|
AddressCode: addressCode,
|
|
|
|
|
Abandoned: abandoned,
|
|
|
|
|
Address: addressInfo["province"] + addressInfo["city"] + addressInfo["district"],
|
|
|
|
|
AddressTree: addressTree,
|
|
|
|
|
Birthday: birthday,
|
2021-01-27 11:29:38 +08:00
|
|
|
|
Constellation: getConstellation(code["birthdayCode"]),
|
|
|
|
|
ChineseZodiac: getChineseZodiac(code["birthdayCode"]),
|
2021-01-11 18:48:50 +08:00
|
|
|
|
Sex: sex,
|
|
|
|
|
Length: length,
|
2021-01-12 14:18:17 +08:00
|
|
|
|
CheckBit: code["checkBit"],
|
2021-01-11 18:48:50 +08:00
|
|
|
|
}, nil
|
2021-01-10 14:56:35 +08:00
|
|
|
|
}
|
2021-01-10 19:22:33 +08:00
|
|
|
|
|
2021-01-11 17:55:24 +08:00
|
|
|
|
// 生成假身份证号码
|
2021-01-12 11:18:07 +08:00
|
|
|
|
func FakeId() string {
|
|
|
|
|
return FakeRequireId(true, "", "", 0)
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 按要求生成假身份证号码
|
2021-01-12 14:18:17 +08:00
|
|
|
|
// isEighteen 是否生成18位号码
|
|
|
|
|
// address 省市县三级地区官方全称:如`北京市`、`台湾省`、`香港特别行政区`、`深圳市`、`黄浦区`
|
|
|
|
|
// birthday 出生日期:如 `2000`、`198801`、`19990101`
|
|
|
|
|
// sex 性别:1为男性,0为女性
|
2021-01-12 11:18:07 +08:00
|
|
|
|
func FakeRequireId(isEighteen bool, address string, birthday string, sex int) string {
|
2021-01-10 19:22:33 +08:00
|
|
|
|
// 生成地址码
|
2021-01-27 11:29:38 +08:00
|
|
|
|
addressCode := generatorAddressCode(address)
|
2021-01-10 19:22:33 +08:00
|
|
|
|
|
|
|
|
|
// 出生日期码
|
2021-01-27 11:29:38 +08:00
|
|
|
|
birthdayCode := generatorBirthdayCode(birthday)
|
2021-01-11 17:55:24 +08:00
|
|
|
|
|
|
|
|
|
// 生成顺序码
|
2021-01-27 11:29:38 +08:00
|
|
|
|
orderCode := generatorOrderCode(sex)
|
2021-01-10 19:22:33 +08:00
|
|
|
|
|
|
|
|
|
if !isEighteen {
|
2021-01-27 11:29:38 +08:00
|
|
|
|
return addressCode + substr(birthdayCode, 2, 8) + orderCode
|
2021-01-10 19:22:33 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
body := addressCode + birthdayCode + orderCode
|
|
|
|
|
|
2021-01-27 11:29:38 +08:00
|
|
|
|
return body + generatorCheckBit(body)
|
2021-01-10 19:22:33 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// 15位升级18位号码
|
2021-01-12 11:52:18 +08:00
|
|
|
|
func UpgradeId(id string) (string, error) {
|
2021-01-10 19:22:33 +08:00
|
|
|
|
if !IsValid(id) {
|
|
|
|
|
return "", errors.New("Not Valid ID card number.")
|
|
|
|
|
}
|
|
|
|
|
|
2021-01-27 11:29:38 +08:00
|
|
|
|
code, _ := generateShortCode(id)
|
2021-01-11 17:55:24 +08:00
|
|
|
|
|
2021-01-10 19:22:33 +08:00
|
|
|
|
body := code["addressCode"] + code["birthdayCode"] + code["order"]
|
|
|
|
|
|
2021-01-27 11:29:38 +08:00
|
|
|
|
return body + generatorCheckBit(body), nil
|
2021-01-10 19:22:33 +08:00
|
|
|
|
}
|