Files
phylum/server/internal/core/password.go
T
2025-06-05 21:32:52 +05:30

58 lines
1.6 KiB
Go

package core
import (
"net/http"
"strconv"
)
type charType int
const (
charTypeOther charType = iota
charTypeLower
charTypeUpper
charTypeNumeric
charTypeSymbol
)
var charTypes = map[rune]charType{}
func init() {
for _, c := range "abcdefghijklmnopqrstuvwxyz" {
charTypes[c] = charTypeLower
}
for _, c := range "ABCDEFGHIJKLMNOPQRSTUVWXYZ" {
charTypes[c] = charTypeUpper
}
for _, c := range "0123456789" {
charTypes[c] = charTypeNumeric
}
for _, c := range "`~!@#$%^&*()-_=+[]{}\\|;:'\",.<>/?" {
charTypes[c] = charTypeSymbol
}
}
func checkPasswordStrength(password string) error {
if len(password) < Cfg.Password.Length {
return NewError(http.StatusBadRequest, "password_invalid", "Must be at least "+strconv.Itoa(Cfg.Password.Length)+" characters long.")
}
count := map[charType]int{}
for _, c := range password {
count[charTypes[c]]++
}
if count[charTypeLower] < Cfg.Password.Lower {
return NewError(http.StatusBadRequest, "password_invalid", "Must have at least "+strconv.Itoa(Cfg.Password.Lower)+" lower case.")
}
if count[charTypeUpper] < Cfg.Password.Upper {
return NewError(http.StatusBadRequest, "password_invalid", "Must have at least "+strconv.Itoa(Cfg.Password.Upper)+" upper case.")
}
if count[charTypeNumeric] < Cfg.Password.Numeric {
return NewError(http.StatusBadRequest, "password_invalid", "Must have at least "+strconv.Itoa(Cfg.Password.Numeric)+" numeric.")
}
if count[charTypeSymbol] < Cfg.Password.Symbols {
return NewError(http.StatusBadRequest, "password_invalid", "Must have at least "+strconv.Itoa(Cfg.Password.Symbols)+" symbols.")
}
return nil
}