mirror of
https://github.com/hacdias/webdav.git
synced 2026-09-22 03:20:41 +08:00
refactor: code cleanup, stricter config validation (#155)
This commit is contained in:
Executable → Regular
+39
-37
@@ -1,50 +1,52 @@
|
||||
package lib
|
||||
|
||||
import (
|
||||
"regexp"
|
||||
"errors"
|
||||
"fmt"
|
||||
"os"
|
||||
"strings"
|
||||
|
||||
"golang.org/x/net/webdav"
|
||||
"golang.org/x/crypto/bcrypt"
|
||||
)
|
||||
|
||||
// Rule is a disallow/allow rule.
|
||||
type Rule struct {
|
||||
Regex bool
|
||||
Allow bool
|
||||
Modify bool
|
||||
Path string
|
||||
Regexp *regexp.Regexp
|
||||
}
|
||||
|
||||
// User contains the settings of each user.
|
||||
type User struct {
|
||||
Username string
|
||||
Password string
|
||||
Scope string
|
||||
Modify bool
|
||||
Rules []*Rule
|
||||
Handler *webdav.Handler
|
||||
Permissions `mapstructure:",squash"`
|
||||
Username string
|
||||
Password string
|
||||
}
|
||||
|
||||
// Allowed checks if the user has permission to access a directory/file
|
||||
func (u User) Allowed(url string, noModification bool) bool {
|
||||
var rule *Rule
|
||||
i := len(u.Rules) - 1
|
||||
|
||||
for i >= 0 {
|
||||
rule = u.Rules[i]
|
||||
|
||||
isAllowed := rule.Allow && (noModification || rule.Modify)
|
||||
if rule.Regex {
|
||||
if rule.Regexp.MatchString(url) {
|
||||
return isAllowed
|
||||
}
|
||||
} else if strings.HasPrefix(url, rule.Path) {
|
||||
return isAllowed
|
||||
}
|
||||
|
||||
i--
|
||||
func (u User) checkPassword(input string) bool {
|
||||
if strings.HasPrefix(u.Password, "{bcrypt}") {
|
||||
savedPassword := strings.TrimPrefix(u.Password, "{bcrypt}")
|
||||
return bcrypt.CompareHashAndPassword([]byte(savedPassword), []byte(input)) == nil
|
||||
}
|
||||
|
||||
return noModification || u.Modify
|
||||
return u.Password == input
|
||||
}
|
||||
|
||||
func (u *User) Validate() error {
|
||||
if u.Username == "" {
|
||||
return errors.New("invalid user: username must be set")
|
||||
}
|
||||
|
||||
if u.Password == "" {
|
||||
return fmt.Errorf("invalid user %q: password must be set", u.Username)
|
||||
} else if strings.HasPrefix(u.Password, "{env}") {
|
||||
|
||||
env := strings.TrimPrefix(u.Password, "{env}")
|
||||
if env == "" {
|
||||
return fmt.Errorf("invalid user %q: password environment variable not set", u.Username)
|
||||
}
|
||||
|
||||
u.Password = os.Getenv(env)
|
||||
if u.Password == "" {
|
||||
return fmt.Errorf("invalid user %q: password environment variable is empty", u.Username)
|
||||
}
|
||||
}
|
||||
|
||||
if err := u.Permissions.Validate(); err != nil {
|
||||
return fmt.Errorf("invalid user %q: %w", u.Username, err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user