mirror of https://github.com/Xhofe/alist
feat(user): enhance path management and role handling (#9249)
- Add `GetUsersByRole` function for fetching users by role. - Introduce `GetAllBasePathsFromRoles` to aggregate paths from roles. - Refine path handling in `pkg/utils/path.go` for normalization. - Comment out base path prefix updates to simplify role operations.pull/9265/head v3.49.0
parent
85fe4e5bb3
commit
6b2d81eede
|
@ -149,9 +149,21 @@ func (u *User) JoinPath(reqPath string) (string, error) {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
if u.CheckPathLimit() && !utils.IsSubPath(u.BasePath, path) {
|
|
||||||
|
if u.CheckPathLimit() {
|
||||||
|
basePaths := GetAllBasePathsFromRoles(u)
|
||||||
|
match := false
|
||||||
|
for _, base := range basePaths {
|
||||||
|
if utils.IsSubPath(base, path) {
|
||||||
|
match = true
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if !match {
|
||||||
return "", errs.PermissionDenied
|
return "", errs.PermissionDenied
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return path, nil
|
return path, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -193,3 +205,22 @@ func (u *User) WebAuthnCredentials() []webauthn.Credential {
|
||||||
func (u *User) WebAuthnIcon() string {
|
func (u *User) WebAuthnIcon() string {
|
||||||
return "https://alistgo.com/logo.svg"
|
return "https://alistgo.com/logo.svg"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GetAllBasePathsFromRoles returns all permission paths from user's roles
|
||||||
|
func GetAllBasePathsFromRoles(u *User) []string {
|
||||||
|
basePaths := make([]string, 0)
|
||||||
|
seen := make(map[string]struct{})
|
||||||
|
|
||||||
|
for _, role := range u.RolesDetail {
|
||||||
|
for _, entry := range role.PermissionScopes {
|
||||||
|
if entry.Path == "" {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if _, ok := seen[entry.Path]; !ok {
|
||||||
|
basePaths = append(basePaths, entry.Path)
|
||||||
|
seen[entry.Path] = struct{}{}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return basePaths
|
||||||
|
}
|
||||||
|
|
|
@ -2,7 +2,6 @@ package op
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/pkg/errors"
|
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/Xhofe/go-cache"
|
"github.com/Xhofe/go-cache"
|
||||||
|
@ -106,26 +105,26 @@ func UpdateRole(r *model.Role) error {
|
||||||
for i := range r.PermissionScopes {
|
for i := range r.PermissionScopes {
|
||||||
r.PermissionScopes[i].Path = utils.FixAndCleanPath(r.PermissionScopes[i].Path)
|
r.PermissionScopes[i].Path = utils.FixAndCleanPath(r.PermissionScopes[i].Path)
|
||||||
}
|
}
|
||||||
if len(old.PermissionScopes) > 0 && len(r.PermissionScopes) > 0 &&
|
//if len(old.PermissionScopes) > 0 && len(r.PermissionScopes) > 0 &&
|
||||||
old.PermissionScopes[0].Path != r.PermissionScopes[0].Path {
|
// old.PermissionScopes[0].Path != r.PermissionScopes[0].Path {
|
||||||
|
//
|
||||||
oldPath := old.PermissionScopes[0].Path
|
// oldPath := old.PermissionScopes[0].Path
|
||||||
newPath := r.PermissionScopes[0].Path
|
// newPath := r.PermissionScopes[0].Path
|
||||||
|
//
|
||||||
users, err := db.GetUsersByRole(int(r.ID))
|
// users, err := db.GetUsersByRole(int(r.ID))
|
||||||
if err != nil {
|
// if err != nil {
|
||||||
return errors.WithMessage(err, "failed to get users by role")
|
// return errors.WithMessage(err, "failed to get users by role")
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
modifiedUsernames, err := db.UpdateUserBasePathPrefix(oldPath, newPath, users)
|
// modifiedUsernames, err := db.UpdateUserBasePathPrefix(oldPath, newPath, users)
|
||||||
if err != nil {
|
// if err != nil {
|
||||||
return errors.WithMessage(err, "failed to update user base path when role updated")
|
// return errors.WithMessage(err, "failed to update user base path when role updated")
|
||||||
}
|
// }
|
||||||
|
//
|
||||||
for _, name := range modifiedUsernames {
|
// for _, name := range modifiedUsernames {
|
||||||
userCache.Del(name)
|
// userCache.Del(name)
|
||||||
}
|
// }
|
||||||
}
|
//}
|
||||||
roleCache.Del(fmt.Sprint(r.ID))
|
roleCache.Del(fmt.Sprint(r.ID))
|
||||||
roleCache.Del(r.Name)
|
roleCache.Del(r.Name)
|
||||||
return db.UpdateRole(r)
|
return db.UpdateRole(r)
|
||||||
|
|
|
@ -232,12 +232,20 @@ func UpdateStorage(ctx context.Context, storage model.Storage) error {
|
||||||
roleCache.Del(fmt.Sprint(id))
|
roleCache.Del(fmt.Sprint(id))
|
||||||
}
|
}
|
||||||
|
|
||||||
modifiedUsernames, err := db.UpdateUserBasePathPrefix(oldStorage.MountPath, storage.MountPath)
|
//modifiedUsernames, err := db.UpdateUserBasePathPrefix(oldStorage.MountPath, storage.MountPath)
|
||||||
|
//if err != nil {
|
||||||
|
// return errors.WithMessage(err, "failed to update user base path")
|
||||||
|
//}
|
||||||
|
for _, id := range modifiedRoleIDs {
|
||||||
|
roleCache.Del(fmt.Sprint(id))
|
||||||
|
|
||||||
|
users, err := db.GetUsersByRole(int(id))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.WithMessage(err, "failed to update user base path")
|
return errors.WithMessage(err, "failed to get users by role")
|
||||||
|
}
|
||||||
|
for _, user := range users {
|
||||||
|
userCache.Del(user.Username)
|
||||||
}
|
}
|
||||||
for _, name := range modifiedUsernames {
|
|
||||||
userCache.Del(name)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|
|
@ -50,6 +50,10 @@ func GetUserByRole(role int) (*model.User, error) {
|
||||||
return db.GetUserByRole(role)
|
return db.GetUserByRole(role)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func GetUsersByRole(role int) ([]model.User, error) {
|
||||||
|
return db.GetUsersByRole(role)
|
||||||
|
}
|
||||||
|
|
||||||
func GetUserByName(username string) (*model.User, error) {
|
func GetUserByName(username string) (*model.User, error) {
|
||||||
if username == "" {
|
if username == "" {
|
||||||
return nil, errs.EmptyUsername
|
return nil, errs.EmptyUsername
|
||||||
|
@ -124,17 +128,17 @@ func UpdateUser(u *model.User) error {
|
||||||
}
|
}
|
||||||
userCache.Del(old.Username)
|
userCache.Del(old.Username)
|
||||||
u.BasePath = utils.FixAndCleanPath(u.BasePath)
|
u.BasePath = utils.FixAndCleanPath(u.BasePath)
|
||||||
if len(u.Role) > 0 {
|
//if len(u.Role) > 0 {
|
||||||
roles, err := GetRolesByUserID(u.ID)
|
// roles, err := GetRolesByUserID(u.ID)
|
||||||
if err == nil {
|
// if err == nil {
|
||||||
for _, role := range roles {
|
// for _, role := range roles {
|
||||||
if len(role.PermissionScopes) > 0 {
|
// if len(role.PermissionScopes) > 0 {
|
||||||
u.BasePath = utils.FixAndCleanPath(role.PermissionScopes[0].Path)
|
// u.BasePath = utils.FixAndCleanPath(role.PermissionScopes[0].Path)
|
||||||
break
|
// break
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
}
|
//}
|
||||||
return db.UpdateUser(u)
|
return db.UpdateUser(u)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -88,6 +88,13 @@ func JoinBasePath(basePath, reqPath string) (string, error) {
|
||||||
strings.Contains(reqPath, "/../") {
|
strings.Contains(reqPath, "/../") {
|
||||||
return "", errs.RelativePath
|
return "", errs.RelativePath
|
||||||
}
|
}
|
||||||
|
|
||||||
|
reqPath = FixAndCleanPath(reqPath)
|
||||||
|
|
||||||
|
if strings.HasPrefix(reqPath, "/") {
|
||||||
|
return reqPath, nil
|
||||||
|
}
|
||||||
|
|
||||||
return stdpath.Join(FixAndCleanPath(basePath), FixAndCleanPath(reqPath)), nil
|
return stdpath.Join(FixAndCleanPath(basePath), FixAndCleanPath(reqPath)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue