id-validator/generator.go

185 lines
4.0 KiB
Go
Raw Normal View History

2021-01-11 17:55:24 +08:00
package idvalidator
2021-01-10 19:22:33 +08:00
import (
2021-01-12 11:36:44 +08:00
"github.com/guanguans/id-validator/data"
2021-01-10 19:22:33 +08:00
"math"
"math/rand"
"regexp"
"strconv"
"strings"
"time"
)
2021-01-11 17:55:24 +08:00
// 生成Bit码
func generatorCheckBit(body string) string {
2021-01-10 19:22:33 +08:00
// 位置加权
var posWeight [19]float64
for i := 2; i < 19; i++ {
weight := int(math.Pow(2, float64(i-1))) % 11
posWeight[i] = float64(weight)
}
2021-01-11 17:55:24 +08:00
// 累身份证号body部分与位置加权的积
var bodySum int
2021-01-10 19:22:33 +08:00
bodyArray := strings.Split(body, "")
count := len(bodyArray)
for i := 0; i < count; i++ {
2021-01-11 17:55:24 +08:00
bodySub, _ := strconv.Atoi(bodyArray[i])
bodySum += bodySub * int(posWeight[18-i])
2021-01-10 19:22:33 +08:00
}
// 生成校验码
checkBit := (12 - (bodySum % 11)) % 11
if checkBit == 10 {
return "X"
}
return strconv.Itoa(checkBit)
}
// 生成地址码
func generatorAddressCode(address string) string {
2021-01-11 17:55:24 +08:00
addressCode := ""
2021-01-10 19:22:33 +08:00
for code, addressStr := range data.AddressCode {
if address == addressStr {
2021-01-11 17:55:24 +08:00
addressCode = strconv.Itoa(code)
2021-01-10 19:22:33 +08:00
break
}
}
classification := addressCodeClassification(addressCode)
2021-01-10 19:22:33 +08:00
switch classification {
case "country":
// addressCode = getRandAddressCode("\\d{4}(?!00)[0-9]{2}$")
addressCode = getRandAddressCode("\\d{4}(?)[0-9]{2}$")
2021-01-10 19:22:33 +08:00
case "province":
provinceCode := substr(addressCode, 0, 2)
2021-01-10 19:22:33 +08:00
// pattern := "^" + provinceCode + "\\d{2}(?!00)[0-9]{2}$"
pattern := "^" + provinceCode + "\\d{2}(?)[0-9]{2}$"
addressCode = getRandAddressCode(pattern)
2021-01-10 19:22:33 +08:00
case "city":
cityCode := substr(addressCode, 0, 4)
2021-01-10 19:22:33 +08:00
// pattern := "^" + cityCode + "(?!00)[0-9]{2}$"
pattern := "^" + cityCode + "(?)[0-9]{2}$"
addressCode = getRandAddressCode(pattern)
2021-01-10 19:22:33 +08:00
}
return addressCode
}
// 地址码分类
func addressCodeClassification(addressCode string) string {
2021-01-10 19:22:33 +08:00
// 全国
if addressCode == "" {
return "country"
}
// 港澳台
if substr(addressCode, 0, 1) == "8" {
2021-01-10 19:22:33 +08:00
return "special"
}
// 省级
if substr(addressCode, 2, 6) == "0000" {
2021-01-10 19:22:33 +08:00
return "province"
}
// 市级
if substr(addressCode, 4, 6) == "00" {
2021-01-10 19:22:33 +08:00
return "city"
}
// 县级
return "district"
}
// 获取随机地址码
func getRandAddressCode(pattern string) string {
2021-01-10 19:22:33 +08:00
mustCompile := regexp.MustCompile(pattern)
var keys []string
2021-01-11 11:53:22 +08:00
for key := range data.AddressCode {
2021-01-10 19:22:33 +08:00
keyStr := strconv.Itoa(key)
if mustCompile.MatchString(keyStr) && substr(keyStr, 4, 6) != "00" {
2021-01-10 19:22:33 +08:00
keys = append(keys, keyStr)
}
}
rand.Seed(time.Now().Unix())
2021-01-11 17:55:24 +08:00
return keys[rand.Intn(len(keys))]
2021-01-10 19:22:33 +08:00
}
// 生成出生日期码
func generatorBirthdayCode(birthday string) string {
year := datePipelineHandle(datePad(substr(birthday, 0, 4), "year"), "year")
month := datePipelineHandle(datePad(substr(birthday, 4, 6), "month"), "month")
day := datePipelineHandle(datePad(substr(birthday, 6, 8), "day"), "day")
2021-01-10 19:22:33 +08:00
2021-01-11 17:55:24 +08:00
birthday = year + month + day
_, error := time.Parse("20060102", birthday)
// example: 195578
if error != nil {
year = datePad(year, "year")
month = datePad(month, "month")
day = datePad(day, "day")
2021-01-10 19:22:33 +08:00
}
2021-01-11 17:55:24 +08:00
return year + month + day
}
2021-01-10 19:22:33 +08:00
2021-01-11 17:55:24 +08:00
// 日期处理
func datePipelineHandle(date string, category string) string {
2021-01-11 17:55:24 +08:00
dateInt, _ := strconv.Atoi(date)
switch category {
case "year":
nowYear := time.Now().Year()
rand.Seed(time.Now().Unix())
if dateInt < 1800 || dateInt > nowYear {
randDate := rand.Intn(nowYear-1950) + 1950
date = strconv.Itoa(randDate)
}
case "month":
if dateInt < 1 || dateInt > 12 {
randDate := rand.Intn(12-1) + 1
date = strconv.Itoa(randDate)
}
2021-01-10 19:22:33 +08:00
2021-01-11 17:55:24 +08:00
case "day":
if dateInt < 1 || dateInt > 31 {
randDate := rand.Intn(28-1) + 1
date = strconv.Itoa(randDate)
}
2021-01-10 19:22:33 +08:00
}
2021-01-11 17:55:24 +08:00
return date
2021-01-10 19:22:33 +08:00
}
// 生成顺序码
func generatorOrderCode(sex int) string {
2021-01-10 19:22:33 +08:00
rand.Seed(time.Now().Unix())
orderCode := rand.Intn(999-111) + 111
if sex != orderCode%2 {
2021-01-11 17:55:24 +08:00
orderCode--
2021-01-10 19:22:33 +08:00
}
return strconv.Itoa(orderCode)
}
// 日期补全
func datePad(date string, category string) string {
2021-01-10 19:22:33 +08:00
padLength := 2
if category == "year" {
padLength = 4
}
2021-01-11 11:53:22 +08:00
for i := 0; i < padLength; i++ {
length := len([]rune(date))
if length < padLength {
// date = fmt.Sprintf("%s%s", "0", date)
date = "0" + date
}
}
return date
2021-01-10 19:22:33 +08:00
}