123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141 |
- // Copyright 2019 github.com. All rights reserved.
- // Use of this source code is governed by github.com.
- package util
- import (
- "regexp"
- )
- const (
- // 匹配大陆电话
- cnPhonePattern = `((\d{3,4})-?)?` + // 区号
- `\d{5,10}` + // 号码,95500等5位数的,7位,8位,以及400开头的10位数
- `(-\d{1,4})?` // 分机号,分机号的连接符号不能省略。
- // 匹配大陆手机号码
- cnMobilePattern = `(0|\+?86)?` + // 匹配 0,86,+86
- `(13[0-9]|` + // 130-139
- `14[579]|` + // 145,147,149
- `15[0-9]|` + // 150-159
- `17[0-9]|` + // 170-179
- `18[0-9]|` + // 180-189
- `16[56]|` + // 165,1666
- `19[0126789])` + // 191,198,199
- `[0-9]{8}`
- // 匹配大陆手机号或是电话号码
- cnTelPattern = "(" + cnPhonePattern + ")|(" + cnMobilePattern + ")"
- // 匹配邮箱
- emailPattern = `^\w+([-+.]\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*$`
- // 匹配 IP4
- ip4Pattern = `((25[0-5]|2[0-4]\d|[01]?\d\d?)\.){3}(25[0-5]|2[0-4]\d|[01]?\d\d?)`
- // 匹配 IP6,参考以下网页内容:
- // http://blog.csdn.net/jiangfeng08/article/details/7642018
- ip6Pattern = `(([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))|` +
- `(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|` +
- `(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})|:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3})|:))|` +
- `(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|` +
- `(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|` +
- `(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|` +
- `(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))|` +
- `(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)(\.(25[0-5]|2[0-4]\d|1\d\d|[1-9]?\d)){3}))|:))`
- // 同时匹配 IP4 和 IP6
- ipPattern = "(" + ip4Pattern + ")|(" + ip6Pattern + ")"
- // 匹配域名
- domainPattern = `[a-zA-Z0-9][a-zA-Z0-9_-]{0,62}(\.[a-zA-Z0-9][a-zA-Z0-9_-]{0,62})*(\.[a-zA-Z][a-zA-Z0-9]{0,10}){1}`
- // 匹配 URL
- urlPattern = `((https|http|ftp|rtsp|mms)?://)?` + // 协议
- `(([0-9a-zA-Z]+:)?[0-9a-zA-Z_-]+@)?` + // pwd:user@
- "(" + ipPattern + "|(" + domainPattern + "))" + // IP 或域名
- `(:\d{1,5})?` + // 端口
- `(/+[a-zA-Z0-9][a-zA-Z0-9_.-]*)*/*` + // path
- `(\?([a-zA-Z0-9_-]+(=.*&?)*)*)*` // query
- idCertPattern = `^[1-9]\d{5}(18|19|20)\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|10|20|30|31)\d{3}[0-9Xx]$`
- )
- var (
- email = regexpCompile(emailPattern)
- ip4 = regexpCompile(ip4Pattern)
- ip6 = regexpCompile(ip6Pattern)
- ip = regexpCompile(ipPattern)
- url = regexpCompile(urlPattern)
- cnPhone = regexpCompile(cnPhonePattern)
- cnMobile = regexpCompile(cnMobilePattern)
- cnTel = regexpCompile(cnTelPattern)
- cnIdCert = regexpCompile(idCertPattern)
- )
- func regexpCompile(str string) *regexp.Regexp {
- return regexp.MustCompile("^" + str + "$")
- }
- // 判断val是否能正确匹配exp中的正则表达式。
- // val可以是[]byte, []rune, string类型。
- func isMatch(exp *regexp.Regexp, val interface{}) bool {
- switch v := val.(type) {
- case []rune:
- return exp.MatchString(string(v))
- case []byte:
- return exp.Match(v)
- case string:
- return exp.MatchString(v)
- default:
- return false
- }
- }
- // IsCNPhone 验证中国大陆的电话号码。支持如下格式:
- // 0578-12345678-1234
- // 057812345678-1234
- // 若存在分机号,则分机号的连接符不能省略。
- func IsCNPhone(val interface{}) bool {
- return isMatch(cnPhone, val)
- }
- // IsCNMobile 验证中国大陆的手机号码
- func IsCNMobile(val interface{}) bool {
- return isMatch(cnMobile, val)
- }
- // IsCNTel 验证手机和电话类型
- func IsCNTel(val interface{}) bool {
- return isMatch(cnTel, val)
- }
- // IsURL 验证一个值是否标准的URL格式。支持IP和域名等格式
- func IsURL(val interface{}) bool {
- return isMatch(url, val)
- }
- // IsIP 验证一个值是否为IP,可验证IP4和IP6
- func IsIP(val interface{}) bool {
- return isMatch(ip, val)
- }
- // IsIP6 验证一个值是否为IP6
- func IsIP6(val interface{}) bool {
- return isMatch(ip6, val)
- }
- // IsIP4 验证一个值是滞为IP4
- func IsIP4(val interface{}) bool {
- return isMatch(ip4, val)
- }
- // IsEmail 验证一个值是否匹配一个邮箱。
- func IsEmail(val interface{}) bool {
- return isMatch(email, val)
- }
- // IsIdCert 验证一个值是否匹配身份证号码。
- func IsIdCert(val interface{}) bool {
- return isMatch(cnIdCert, val)
- }
|