move other errors to utils package

This commit is contained in:
Nicola Murino 2021-06-19 13:06:01 +02:00
parent f19937b715
commit c1b862394d
No known key found for this signature in database
GPG key ID: 2F1FB59433D5A8CB
13 changed files with 79 additions and 73 deletions

View file

@ -12,7 +12,6 @@ import (
"github.com/yl2chen/cidranger"
"github.com/drakkan/sftpgo/dataprovider"
"github.com/drakkan/sftpgo/logger"
"github.com/drakkan/sftpgo/utils"
)
@ -280,7 +279,7 @@ func (d *memoryDefender) GetHost(ip string) (*DefenderEntry, error) {
}, nil
}
return nil, dataprovider.NewRecordNotFoundError("host not found")
return nil, utils.NewRecordNotFoundError("host not found")
}
// IsBanned returns true if the specified IP is banned

View file

@ -160,7 +160,7 @@ func (p *BoltProvider) updateLastLogin(username string) error {
}
var u []byte
if u = bucket.Get([]byte(username)); u == nil {
return &RecordNotFoundError{err: fmt.Sprintf("username %#v does not exist, unable to update last login", username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("username %#v does not exist, unable to update last login", username))
}
var user User
err = json.Unmarshal(u, &user)
@ -190,7 +190,7 @@ func (p *BoltProvider) updateQuota(username string, filesAdd int, sizeAdd int64,
}
var u []byte
if u = bucket.Get([]byte(username)); u == nil {
return &RecordNotFoundError{err: fmt.Sprintf("username %#v does not exist, unable to update quota", username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("username %#v does not exist, unable to update quota", username))
}
var user User
err = json.Unmarshal(u, &user)
@ -235,7 +235,7 @@ func (p *BoltProvider) adminExists(username string) (Admin, error) {
}
a := bucket.Get([]byte(username))
if a == nil {
return &RecordNotFoundError{err: fmt.Sprintf("admin %v does not exist", username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("admin %v does not exist", username))
}
return json.Unmarshal(a, &admin)
})
@ -282,7 +282,7 @@ func (p *BoltProvider) updateAdmin(admin *Admin) error {
var a []byte
if a = bucket.Get([]byte(admin.Username)); a == nil {
return &RecordNotFoundError{err: fmt.Sprintf("admin %v does not exist", admin.Username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("admin %v does not exist", admin.Username))
}
var oldAdmin Admin
err = json.Unmarshal(a, &oldAdmin)
@ -307,7 +307,7 @@ func (p *BoltProvider) deleteAdmin(admin *Admin) error {
}
if bucket.Get([]byte(admin.Username)) == nil {
return &RecordNotFoundError{err: fmt.Sprintf("admin %v does not exist", admin.Username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("admin %v does not exist", admin.Username))
}
return bucket.Delete([]byte(admin.Username))
@ -397,7 +397,7 @@ func (p *BoltProvider) userExists(username string) (User, error) {
}
u := bucket.Get([]byte(username))
if u == nil {
return &RecordNotFoundError{err: fmt.Sprintf("username %#v does not exist", username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("username %#v does not exist", username))
}
folderBucket, err := getFoldersBucket(tx)
if err != nil {
@ -465,7 +465,7 @@ func (p *BoltProvider) updateUser(user *User) error {
}
var u []byte
if u = bucket.Get([]byte(user.Username)); u == nil {
return &RecordNotFoundError{err: fmt.Sprintf("username %#v does not exist", user.Username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("username %#v does not exist", user.Username))
}
var oldUser User
err = json.Unmarshal(u, &oldUser)
@ -517,7 +517,7 @@ func (p *BoltProvider) deleteUser(user *User) error {
}
exists := bucket.Get([]byte(user.Username))
if exists == nil {
return &RecordNotFoundError{err: fmt.Sprintf("user %#v does not exist", user.Username)}
return utils.NewRecordNotFoundError(fmt.Sprintf("user %#v does not exist", user.Username))
}
return bucket.Delete([]byte(user.Username))
})
@ -722,7 +722,7 @@ func (p *BoltProvider) updateFolder(folder *vfs.BaseVirtualFolder) error {
var f []byte
if f = bucket.Get([]byte(folder.Name)); f == nil {
return &RecordNotFoundError{err: fmt.Sprintf("folder %v does not exist", folder.Name)}
return utils.NewRecordNotFoundError(fmt.Sprintf("folder %v does not exist", folder.Name))
}
var oldFolder vfs.BaseVirtualFolder
err = json.Unmarshal(f, &oldFolder)
@ -755,7 +755,7 @@ func (p *BoltProvider) deleteFolder(folder *vfs.BaseVirtualFolder) error {
}
var f []byte
if f = bucket.Get([]byte(folder.Name)); f == nil {
return &RecordNotFoundError{err: fmt.Sprintf("folder %v does not exist", folder.Name)}
return utils.NewRecordNotFoundError(fmt.Sprintf("folder %v does not exist", folder.Name))
}
var folder vfs.BaseVirtualFolder
err = json.Unmarshal(f, &folder)
@ -801,7 +801,7 @@ func (p *BoltProvider) updateFolderQuota(name string, filesAdd int, sizeAdd int6
}
var f []byte
if f = bucket.Get([]byte(name)); f == nil {
return &RecordNotFoundError{err: fmt.Sprintf("folder %#v does not exist, unable to update quota", name)}
return utils.NewRecordNotFoundError(fmt.Sprintf("folder %#v does not exist, unable to update quota", name))
}
var folder vfs.BaseVirtualFolder
err = json.Unmarshal(f, &folder)
@ -910,7 +910,7 @@ func folderExistsInternal(name string, bucket *bolt.Bucket) (vfs.BaseVirtualFold
var folder vfs.BaseVirtualFolder
f := bucket.Get([]byte(name))
if f == nil {
err := &RecordNotFoundError{err: fmt.Sprintf("folder %v does not exist", name)}
err := utils.NewRecordNotFoundError(fmt.Sprintf("folder %v does not exist", name))
return folder, err
}
err := json.Unmarshal(f, &folder)

View file

@ -366,34 +366,6 @@ type checkPasswordResponse struct {
ToVerify string `json:"to_verify"`
}
// MethodDisabledError raised if a method is disabled in config file.
// For example, if user management is disabled, this error is raised
// every time a user operation is done using the REST API
type MethodDisabledError struct {
err string
}
// Method disabled error details
func (e *MethodDisabledError) Error() string {
return fmt.Sprintf("Method disabled error: %s", e.err)
}
// RecordNotFoundError raised if a requested user is not found
type RecordNotFoundError struct {
err string
}
func (e *RecordNotFoundError) Error() string {
return fmt.Sprintf("not found: %s", e.err)
}
// NewRecordNotFoundError returns a not found error
func NewRecordNotFoundError(error string) *RecordNotFoundError {
return &RecordNotFoundError{
err: error,
}
}
// GetQuotaTracking returns the configured mode for user's quota tracking
func GetQuotaTracking() int {
return config.TrackQuota
@ -808,7 +780,7 @@ func UpdateLastLogin(user *User) error {
// If reset is true filesAdd and sizeAdd indicates the total files and the total size instead of the difference.
func UpdateUserQuota(user *User, filesAdd int, sizeAdd int64, reset bool) error {
if config.TrackQuota == 0 {
return &MethodDisabledError{err: trackQuotaDisabledError}
return utils.NewMethodDisabledError(trackQuotaDisabledError)
} else if config.TrackQuota == 2 && !reset && !user.HasQuotaRestrictions() {
return nil
}
@ -829,7 +801,7 @@ func UpdateUserQuota(user *User, filesAdd int, sizeAdd int64, reset bool) error
// If reset is true filesAdd and sizeAdd indicates the total files and the total size instead of the difference.
func UpdateVirtualFolderQuota(vfolder *vfs.BaseVirtualFolder, filesAdd int, sizeAdd int64, reset bool) error {
if config.TrackQuota == 0 {
return &MethodDisabledError{err: trackQuotaDisabledError}
return utils.NewMethodDisabledError(trackQuotaDisabledError)
}
if filesAdd == 0 && sizeAdd == 0 && !reset {
return nil
@ -847,7 +819,7 @@ func UpdateVirtualFolderQuota(vfolder *vfs.BaseVirtualFolder, filesAdd int, size
// GetUsedQuota returns the used quota for the given SFTP user.
func GetUsedQuota(username string) (int, int64, error) {
if config.TrackQuota == 0 {
return 0, 0, &MethodDisabledError{err: trackQuotaDisabledError}
return 0, 0, utils.NewMethodDisabledError(trackQuotaDisabledError)
}
files, size, err := provider.getUsedQuota(username)
if err != nil {
@ -860,7 +832,7 @@ func GetUsedQuota(username string) (int, int64, error) {
// GetUsedVirtualFolderQuota returns the used quota for the given virtual folder.
func GetUsedVirtualFolderQuota(name string) (int, int64, error) {
if config.TrackQuota == 0 {
return 0, 0, &MethodDisabledError{err: trackQuotaDisabledError}
return 0, 0, utils.NewMethodDisabledError(trackQuotaDisabledError)
}
files, size, err := provider.getUsedFolderQuota(name)
if err != nil {
@ -2149,7 +2121,7 @@ func executePreLoginHook(username, loginMethod, ip, protocol string) (User, erro
providerLog(logger.LevelDebug, "empty response from pre-login hook, no modification requested for user %#v id: %v",
username, u.ID)
if u.ID == 0 {
return u, &RecordNotFoundError{err: fmt.Sprintf("username %#v does not exist", username)}
return u, utils.NewRecordNotFoundError(fmt.Sprintf("username %#v does not exist", username))
}
return u, nil
}
@ -2345,7 +2317,7 @@ func doExternalAuth(username, password string, pubKey []byte, keyboardInteractiv
providerLog(logger.LevelDebug, "empty response from external hook, no modification requested for user %#v id: %v",
username, u.ID)
if u.ID == 0 {
return u, &RecordNotFoundError{err: fmt.Sprintf("username %#v does not exist", username)}
return u, utils.NewRecordNotFoundError(fmt.Sprintf("username %#v does not exist", username))
}
return u, nil
}
@ -2389,7 +2361,7 @@ func getUserAndJSONForHook(username string) (User, []byte, error) {
var userAsJSON []byte
u, err := provider.userExists(username)
if err != nil {
if _, ok := err.(*RecordNotFoundError); !ok {
if _, ok := err.(*utils.RecordNotFoundError); !ok {
return u, userAsJSON, err
}
u = User{

View file

@ -367,7 +367,7 @@ func (p *MemoryProvider) userExistsInternal(username string) (User, error) {
if val, ok := p.dbHandle.users[username]; ok {
return val.getACopy(), nil
}
return User{}, &RecordNotFoundError{err: fmt.Sprintf("username %#v does not exist", username)}
return User{}, utils.NewRecordNotFoundError(fmt.Sprintf("username %#v does not exist", username))
}
func (p *MemoryProvider) addAdmin(admin *Admin) error {
@ -444,7 +444,7 @@ func (p *MemoryProvider) adminExistsInternal(username string) (Admin, error) {
if val, ok := p.dbHandle.admins[username]; ok {
return val.getACopy(), nil
}
return Admin{}, &RecordNotFoundError{err: fmt.Sprintf("admin %#v does not exist", username)}
return Admin{}, utils.NewRecordNotFoundError(fmt.Sprintf("admin %#v does not exist", username))
}
func (p *MemoryProvider) dumpAdmins() ([]Admin, error) {
@ -594,7 +594,7 @@ func (p *MemoryProvider) addOrUpdateFolderInternal(baseFolder *vfs.BaseVirtualFo
p.updateFoldersMappingInternal(folder)
return folder, nil
}
if _, ok := err.(*RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
folder = baseFolder.GetACopy()
folder.ID = p.getNextFolderID()
folder.UsedQuotaSize = usedQuotaSize
@ -611,7 +611,7 @@ func (p *MemoryProvider) folderExistsInternal(name string) (vfs.BaseVirtualFolde
if val, ok := p.dbHandle.vfolders[name]; ok {
return val, nil
}
return vfs.BaseVirtualFolder{}, &RecordNotFoundError{err: fmt.Sprintf("folder %#v does not exist", name)}
return vfs.BaseVirtualFolder{}, utils.NewRecordNotFoundError(fmt.Sprintf("folder %#v does not exist", name))
}
func (p *MemoryProvider) getFolders(limit, offset int, order string) ([]vfs.BaseVirtualFolder, error) {

View file

@ -494,7 +494,7 @@ func getAdminFromDbRow(row sqlScanner) (Admin, error) {
if err != nil {
if err == sql.ErrNoRows {
return admin, &RecordNotFoundError{err: err.Error()}
return admin, utils.NewRecordNotFoundError(err.Error())
}
return admin, err
}
@ -543,7 +543,7 @@ func getUserFromDbRow(row sqlScanner) (User, error) {
&additionalInfo, &description)
if err != nil {
if err == sql.ErrNoRows {
return user, &RecordNotFoundError{err: err.Error()}
return user, utils.NewRecordNotFoundError(err.Error())
}
return user, err
}
@ -620,7 +620,7 @@ func sqlCommonGetFolder(ctx context.Context, name string, dbHandle sqlQuerier) (
err = row.Scan(&folder.ID, &mappedPath, &folder.UsedQuotaSize, &folder.UsedQuotaFiles, &folder.LastQuotaUpdate,
&folder.Name, &description, &fsConfig)
if err == sql.ErrNoRows {
return folder, &RecordNotFoundError{err: err.Error()}
return folder, utils.NewRecordNotFoundError(err.Error())
}
if mappedPath.Valid {
folder.MappedPath = mappedPath.String

View file

@ -477,7 +477,7 @@ func (u *User) getForbiddenSFTPSelfUsers(username string) ([]string, error) {
}
return forbiddens, nil
}
if _, ok := err.(*RecordNotFoundError); !ok {
if _, ok := err.(*utils.RecordNotFoundError); !ok {
return nil, err
}

View file

@ -353,7 +353,7 @@ func updateLoginMetrics(user *dataprovider.User, ip, loginMethod string, err err
logger.ConnectionFailedLog(user.Username, ip, loginMethod,
common.ProtocolFTP, err.Error())
event := common.HostEventLoginFailed
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
event = common.HostEventUserNotFound
}
common.AddDefenderEvent(ip, event)

View file

@ -45,10 +45,10 @@ func getRespStatus(err error) int {
if _, ok := err.(*utils.ValidationError); ok {
return http.StatusBadRequest
}
if _, ok := err.(*dataprovider.MethodDisabledError); ok {
if _, ok := err.(*utils.MethodDisabledError); ok {
return http.StatusForbidden
}
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
return http.StatusNotFound
}
if os.IsNotExist(err) {
@ -366,7 +366,7 @@ func updateLoginMetrics(user *dataprovider.User, ip string, err error) {
if err != nil && err != common.ErrInternalFailure {
logger.ConnectionFailedLog(user.Username, ip, dataprovider.LoginMethodPassword, common.ProtocolHTTP, err.Error())
event := common.HostEventLoginFailed
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
event = common.HostEventUserNotFound
}
common.AddDefenderEvent(ip, event)

View file

@ -298,7 +298,7 @@ func TestShouldBind(t *testing.T) {
func TestGetRespStatus(t *testing.T) {
var err error
err = &dataprovider.MethodDisabledError{}
err = utils.NewMethodDisabledError("")
respStatus := getRespStatus(err)
assert.Equal(t, http.StatusForbidden, respStatus)
err = fmt.Errorf("generic error")

View file

@ -1146,7 +1146,7 @@ func handleWebUpdateAdminGet(w http.ResponseWriter, r *http.Request) {
admin, err := dataprovider.AdminExists(username)
if err == nil {
renderAddUpdateAdminPage(w, r, &admin, "", false)
} else if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
} else if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
} else {
renderInternalServerErrorPage(w, r, err)
@ -1177,7 +1177,7 @@ func handleWebUpdateAdminPost(w http.ResponseWriter, r *http.Request) {
username := getURLParam(r, "username")
admin, err := dataprovider.AdminExists(username)
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
return
} else if err != nil {
@ -1265,7 +1265,7 @@ func handleWebTemplateFolderGet(w http.ResponseWriter, r *http.Request) {
folder, err := dataprovider.GetFolderByName(name)
if err == nil {
renderFolderPage(w, r, folder, folderPageModeTemplate, "")
} else if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
} else if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
} else {
renderInternalServerErrorPage(w, r, err)
@ -1328,7 +1328,7 @@ func handleWebTemplateUserGet(w http.ResponseWriter, r *http.Request) {
if err == nil {
user.SetEmptySecrets()
renderUserPage(w, r, &user, userPageModeTemplate, "")
} else if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
} else if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
} else {
renderInternalServerErrorPage(w, r, err)
@ -1388,7 +1388,7 @@ func handleWebAddUserGet(w http.ResponseWriter, r *http.Request) {
user.Password = ""
user.SetEmptySecrets()
renderUserPage(w, r, &user, userPageModeAdd, "")
} else if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
} else if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
} else {
renderInternalServerErrorPage(w, r, err)
@ -1404,7 +1404,7 @@ func handleWebUpdateUserGet(w http.ResponseWriter, r *http.Request) {
user, err := dataprovider.UserExists(username)
if err == nil {
renderUserPage(w, r, &user, userPageModeUpdate, "")
} else if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
} else if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
} else {
renderInternalServerErrorPage(w, r, err)
@ -1434,7 +1434,7 @@ func handleWebUpdateUserPost(w http.ResponseWriter, r *http.Request) {
r.Body = http.MaxBytesReader(w, r.Body, maxRequestSize)
username := getURLParam(r, "username")
user, err := dataprovider.UserExists(username)
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
return
} else if err != nil {
@ -1527,7 +1527,7 @@ func handleWebUpdateFolderGet(w http.ResponseWriter, r *http.Request) {
folder, err := dataprovider.GetFolderByName(name)
if err == nil {
renderFolderPage(w, r, folder, folderPageModeUpdate, "")
} else if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
} else if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
} else {
renderInternalServerErrorPage(w, r, err)
@ -1538,7 +1538,7 @@ func handleWebUpdateFolderPost(w http.ResponseWriter, r *http.Request) {
r.Body = http.MaxBytesReader(w, r.Body, maxRequestSize)
name := getURLParam(r, "name")
folder, err := dataprovider.GetFolderByName(name)
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
renderNotFoundPage(w, r, err)
return
} else if err != nil {

View file

@ -845,7 +845,7 @@ func updateLoginMetrics(user *dataprovider.User, ip, method string, err error) {
// record failed login key auth only once for session if the
// authentication fails in checkAuthError
event := common.HostEventLoginFailed
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
event = common.HostEventUserNotFound
}
common.AddDefenderEvent(ip, event)

View file

@ -18,3 +18,38 @@ func NewValidationError(error string) *ValidationError {
err: error,
}
}
// RecordNotFoundError raised if a requested user is not found
type RecordNotFoundError struct {
err string
}
func (e *RecordNotFoundError) Error() string {
return fmt.Sprintf("not found: %s", e.err)
}
// NewRecordNotFoundError returns a not found error
func NewRecordNotFoundError(error string) *RecordNotFoundError {
return &RecordNotFoundError{
err: error,
}
}
// MethodDisabledError raised if a method is disabled in config file.
// For example, if user management is disabled, this error is raised
// every time a user operation is done using the REST API
type MethodDisabledError struct {
err string
}
// Method disabled error details
func (e *MethodDisabledError) Error() string {
return fmt.Sprintf("Method disabled error: %s", e.err)
}
// NewMethodDisabledError returns a method disabled error
func NewMethodDisabledError(error string) *MethodDisabledError {
return &MethodDisabledError{
err: error,
}
}

View file

@ -370,7 +370,7 @@ func updateLoginMetrics(user *dataprovider.User, ip, loginMethod string, err err
if err != nil && err != common.ErrInternalFailure {
logger.ConnectionFailedLog(user.Username, ip, loginMethod, common.ProtocolWebDAV, err.Error())
event := common.HostEventLoginFailed
if _, ok := err.(*dataprovider.RecordNotFoundError); ok {
if _, ok := err.(*utils.RecordNotFoundError); ok {
event = common.HostEventUserNotFound
}
common.AddDefenderEvent(ip, event)