Skip to content

Commit 2c72e55

Browse files
authored
Merge pull request #518 from dims/copy-minimum-we-need-from-asaskevich/govalidator-and-drop-the-dependency
Strip/Freeze code from asaskevich/govalidator and drop dependency
2 parents 5ad02ce + f1ff53c commit 2c72e55

File tree

7 files changed

+586
-5
lines changed

7 files changed

+586
-5
lines changed

go.mod

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@ go 1.21
44

55
require (
66
github.com/NYTimes/gziphandler v1.1.1
7-
github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a
87
github.com/emicklei/go-restful/v3 v3.11.0
98
github.com/go-openapi/jsonreference v0.20.1
109
github.com/go-openapi/swag v0.23.0

go.sum

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,5 @@
11
github.com/NYTimes/gziphandler v1.1.1 h1:ZUDjpQae29j0ryrS0u/B8HZfJBtBQHjqw2rQ2cqUQ3I=
22
github.com/NYTimes/gziphandler v1.1.1/go.mod h1:n/CVRwUEOgIxrgPvAQhUUr9oeUtvrhMomdKFjzJNB0c=
3-
github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a h1:idn718Q4B6AGu/h5Sxe66HYVdqdGu2l9Iebqhi/AEoA=
4-
github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a/go.mod h1:lB+ZfQJz7igIIfQNfa7Ml4HSf2uFQQRzpGGRXenZAgY=
53
github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E=
64
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
75
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
The MIT License (MIT)
2+
3+
Copyright (c) 2014 Alex Saskevich
4+
5+
Permission is hereby granted, free of charge, to any person obtaining a copy
6+
of this software and associated documentation files (the "Software"), to deal
7+
in the Software without restriction, including without limitation the rights
8+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9+
copies of the Software, and to permit persons to whom the Software is
10+
furnished to do so, subject to the following conditions:
11+
12+
The above copyright notice and this permission notice shall be included in all
13+
copies or substantial portions of the Software.
14+
15+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21+
SOFTWARE.
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
package govalidator
2+
3+
import "regexp"
4+
5+
// Basic regular expressions for validating strings
6+
const (
7+
CreditCard string = "^(?:4[0-9]{12}(?:[0-9]{3})?|5[1-5][0-9]{14}|6(?:011|5[0-9][0-9])[0-9]{12}|3[47][0-9]{13}|3(?:0[0-5]|[68][0-9])[0-9]{11}|(?:2131|1800|35\\d{3})\\d{11})$"
8+
ISBN10 string = "^(?:[0-9]{9}X|[0-9]{10})$"
9+
ISBN13 string = "^(?:[0-9]{13})$"
10+
Hexcolor string = "^#?([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$"
11+
RGBcolor string = "^rgb\\(\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*\\)$"
12+
Base64 string = "^(?:[A-Za-z0-9+\\/]{4})*(?:[A-Za-z0-9+\\/]{2}==|[A-Za-z0-9+\\/]{3}=|[A-Za-z0-9+\\/]{4})$"
13+
SSN string = `^\d{3}[- ]?\d{2}[- ]?\d{4}$`
14+
Int string = "^(?:[-+]?(?:0|[1-9][0-9]*))$"
15+
)
16+
17+
var (
18+
rxCreditCard = regexp.MustCompile(CreditCard)
19+
rxInt = regexp.MustCompile(Int)
20+
rxISBN10 = regexp.MustCompile(ISBN10)
21+
rxISBN13 = regexp.MustCompile(ISBN13)
22+
rxHexcolor = regexp.MustCompile(Hexcolor)
23+
rxRGBcolor = regexp.MustCompile(RGBcolor)
24+
rxBase64 = regexp.MustCompile(Base64)
25+
rxSSN = regexp.MustCompile(SSN)
26+
)
Lines changed: 181 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,181 @@
1+
// Package govalidator is package of validators and sanitizers for strings, structs and collections.
2+
package govalidator
3+
4+
import (
5+
"fmt"
6+
"net"
7+
"net/url"
8+
"reflect"
9+
"regexp"
10+
"strconv"
11+
"strings"
12+
)
13+
14+
var (
15+
notNumberRegexp = regexp.MustCompile("[^0-9]+")
16+
whiteSpacesAndMinus = regexp.MustCompile(`[\s-]+`)
17+
)
18+
19+
// IsRequestURI check if the string rawurl, assuming
20+
// it was received in an HTTP request, is an
21+
// absolute URI or an absolute path.
22+
func IsRequestURI(rawurl string) bool {
23+
_, err := url.ParseRequestURI(rawurl)
24+
return err == nil
25+
}
26+
27+
// IsHexcolor check if the string is a hexadecimal color.
28+
func IsHexcolor(str string) bool {
29+
return rxHexcolor.MatchString(str)
30+
}
31+
32+
// IsRGBcolor check if the string is a valid RGB color in form rgb(RRR, GGG, BBB).
33+
func IsRGBcolor(str string) bool {
34+
return rxRGBcolor.MatchString(str)
35+
}
36+
37+
// IsCreditCard check if the string is a credit card.
38+
func IsCreditCard(str string) bool {
39+
sanitized := notNumberRegexp.ReplaceAllString(str, "")
40+
if !rxCreditCard.MatchString(sanitized) {
41+
return false
42+
}
43+
var sum int64
44+
var digit string
45+
var tmpNum int64
46+
var shouldDouble bool
47+
for i := len(sanitized) - 1; i >= 0; i-- {
48+
digit = sanitized[i:(i + 1)]
49+
tmpNum, _ = ToInt(digit)
50+
if shouldDouble {
51+
tmpNum *= 2
52+
if tmpNum >= 10 {
53+
sum += (tmpNum % 10) + 1
54+
} else {
55+
sum += tmpNum
56+
}
57+
} else {
58+
sum += tmpNum
59+
}
60+
shouldDouble = !shouldDouble
61+
}
62+
63+
return sum%10 == 0
64+
}
65+
66+
// IsISBN10 check if the string is an ISBN version 10.
67+
func IsISBN10(str string) bool {
68+
return IsISBN(str, 10)
69+
}
70+
71+
// IsISBN13 check if the string is an ISBN version 13.
72+
func IsISBN13(str string) bool {
73+
return IsISBN(str, 13)
74+
}
75+
76+
// IsISBN check if the string is an ISBN (version 10 or 13).
77+
// If version value is not equal to 10 or 13, it will be check both variants.
78+
func IsISBN(str string, version int) bool {
79+
sanitized := whiteSpacesAndMinus.ReplaceAllString(str, "")
80+
var checksum int32
81+
var i int32
82+
if version == 10 {
83+
if !rxISBN10.MatchString(sanitized) {
84+
return false
85+
}
86+
for i = 0; i < 9; i++ {
87+
checksum += (i + 1) * int32(sanitized[i]-'0')
88+
}
89+
if sanitized[9] == 'X' {
90+
checksum += 10 * 10
91+
} else {
92+
checksum += 10 * int32(sanitized[9]-'0')
93+
}
94+
if checksum%11 == 0 {
95+
return true
96+
}
97+
return false
98+
} else if version == 13 {
99+
if !rxISBN13.MatchString(sanitized) {
100+
return false
101+
}
102+
factor := []int32{1, 3}
103+
for i = 0; i < 12; i++ {
104+
checksum += factor[i%2] * int32(sanitized[i]-'0')
105+
}
106+
return (int32(sanitized[12]-'0'))-((10-(checksum%10))%10) == 0
107+
}
108+
return IsISBN(str, 10) || IsISBN(str, 13)
109+
}
110+
111+
// IsBase64 check if a string is base64 encoded.
112+
func IsBase64(str string) bool {
113+
return rxBase64.MatchString(str)
114+
}
115+
116+
// IsIPv6 check if the string is an IP version 6.
117+
func IsIPv6(str string) bool {
118+
ip := net.ParseIP(str)
119+
return ip != nil && strings.Contains(str, ":")
120+
}
121+
122+
// IsMAC check if a string is valid MAC address.
123+
// Possible MAC formats:
124+
// 01:23:45:67:89:ab
125+
// 01:23:45:67:89:ab:cd:ef
126+
// 01-23-45-67-89-ab
127+
// 01-23-45-67-89-ab-cd-ef
128+
// 0123.4567.89ab
129+
// 0123.4567.89ab.cdef
130+
func IsMAC(str string) bool {
131+
_, err := net.ParseMAC(str)
132+
return err == nil
133+
}
134+
135+
// IsSSN will validate the given string as a U.S. Social Security Number
136+
func IsSSN(str string) bool {
137+
if str == "" || len(str) != 11 {
138+
return false
139+
}
140+
return rxSSN.MatchString(str)
141+
}
142+
143+
// ToInt convert the input string or any int type to an integer type 64, or 0 if the input is not an integer.
144+
func ToInt(value interface{}) (res int64, err error) {
145+
val := reflect.ValueOf(value)
146+
147+
switch value.(type) {
148+
case int, int8, int16, int32, int64:
149+
res = val.Int()
150+
case uint, uint8, uint16, uint32, uint64:
151+
res = int64(val.Uint())
152+
case string:
153+
if IsInt(val.String()) {
154+
res, err = strconv.ParseInt(val.String(), 0, 64)
155+
if err != nil {
156+
res = 0
157+
}
158+
} else {
159+
err = fmt.Errorf("math: square root of negative number %g", value)
160+
res = 0
161+
}
162+
default:
163+
err = fmt.Errorf("math: square root of negative number %g", value)
164+
res = 0
165+
}
166+
167+
return
168+
}
169+
170+
// IsInt check if the string is an integer. Empty string is valid.
171+
func IsInt(str string) bool {
172+
if IsNull(str) {
173+
return true
174+
}
175+
return rxInt.MatchString(str)
176+
}
177+
178+
// IsNull check if the string is null.
179+
func IsNull(str string) bool {
180+
return len(str) == 0
181+
}

0 commit comments

Comments
 (0)