Reputation: 4411
I am building a super simple function to ensure a password contains specific characters. Namely, the password should have the following:
#
, or |
I thought regex would be the simplest way to go about doing this. But, I am having a hard time figuring out how to do this in Golang. Currently, I have a bunch of separate regex MatchString
functions which I will combine to get the desired functionality. For example:
lowercaseMatch := regexp.MustCompile(`[a-z]`).MatchString
uppercaseMatch := regexp.MustCompile(`[A-Z]`).MatchString
digitMatch := regexp.MustCompile(`\d`).MatchString
specialMatch := regexp.MustCompile(`\W`).MatchString
badCharsMatch := regexp.MustCompile(`[\s#|]`).MatchString
if (lowercaseMatch(pwd)
&& uppercaseMatch(pwd)
&& digitMatch(pwd)
&& specialMatch(pwd)
&& !badCharsMatch(pwd)) {
/* password OK */
} else {
/* password BAD */
}
While this makes things pretty readable, I would prefer a more concise regex, but I don't know how to get regex to search for a single character of each of the above categories (regardless of position). Can someone point me in the right direction of how to achieve this? Additionally, if there is a better way to do this than regex, I am all ears.
Thanks!
Upvotes: 1
Views: 1257
Reputation: 22393
Since golang use re2, it doesn't support positive-lookahead (?=regex), so I'm not sure if there is a way to write a regex that cover all cases.
Instead, you can use unicode
package:
func verifyPassword(s string) bool {
var hasNumber, hasUpperCase, hasLowercase, hasSpecial bool
for _, c := range s {
switch {
case unicode.IsNumber(c):
hasNumber = true
case unicode.IsUpper(c):
hasUpperCase = true
case unicode.IsLower(c):
hasLowercase = true
case c == '#' || c == '|':
return false
case unicode.IsPunct(c) || unicode.IsSymbol(c):
hasSpecial = true
}
}
return hasNumber && hasUpperCase && hasLowercase && hasSpecial
}
Upvotes: 4