From 15b4194e8f3a495e918c2a0a1547dcfd345c86e8 Mon Sep 17 00:00:00 2001 From: Nicola Murino Date: Sun, 16 Oct 2022 15:28:47 +0200 Subject: [PATCH] event rules: allow to set min/max file size using "human" notation 10MB or 1GB instead of the size in bytes Signed-off-by: Nicola Murino --- internal/common/eventmanager.go | 19 +++++++++++-------- internal/common/eventmanager_test.go | 10 ++++++++++ internal/dataprovider/eventrule.go | 4 ++-- internal/httpd/webadmin.go | 6 +++--- templates/webadmin/eventrule.html | 10 +++++----- 5 files changed, 31 insertions(+), 18 deletions(-) diff --git a/internal/common/eventmanager.go b/internal/common/eventmanager.go index 17c2377e..1d33c7a0 100644 --- a/internal/common/eventmanager.go +++ b/internal/common/eventmanager.go @@ -836,8 +836,7 @@ func getMailAttachments(user dataprovider.User, attachments []string, replacer * } conn := NewBaseConnection(connectionID, protocolEventAction, "", "", user) totalSize := int64(0) - for _, virtualPath := range attachments { - virtualPath = util.CleanPath(replaceWithReplacer(virtualPath, replacer)) + for _, virtualPath := range replacePathsPlaceholders(attachments, replacer) { info, err := conn.DoStat(virtualPath, 0, false) if err != nil { return nil, fmt.Errorf("unable to get info for file %q, user %q: %w", virtualPath, conn.User.Username, err) @@ -1203,6 +1202,13 @@ func getUserForEventAction(user dataprovider.User) (dataprovider.User, error) { return user, nil } +func replacePathsPlaceholders(paths []string, replacer *strings.Replacer) []string { + for idx := range paths { + paths[idx] = util.CleanPath(replaceWithReplacer(paths[idx], replacer)) + } + return util.RemoveDuplicates(paths, false) +} + func executeDeleteFileFsAction(conn *BaseConnection, item string, info os.FileInfo) error { fs, fsPath, err := conn.GetFsAndResolvedPath(item) if err != nil { @@ -1223,8 +1229,7 @@ func executeDeleteFsActionForUser(deletes []string, replacer *strings.Replacer, return fmt.Errorf("delete error, unable to check root fs for user %q: %w", user.Username, err) } conn := NewBaseConnection(connectionID, protocolEventAction, "", "", user) - for _, item := range deletes { - item = util.CleanPath(replaceWithReplacer(item, replacer)) + for _, item := range replacePathsPlaceholders(deletes, replacer) { info, err := conn.DoStat(item, 0, false) if err != nil { if conn.IsNotExistError(err) { @@ -1298,8 +1303,7 @@ func executeMkDirsFsActionForUser(dirs []string, replacer *strings.Replacer, use return fmt.Errorf("mkdir error, unable to check root fs for user %q: %w", user.Username, err) } conn := NewBaseConnection(connectionID, protocolEventAction, "", "", user) - for _, item := range dirs { - item = util.CleanPath(replaceWithReplacer(item, replacer)) + for _, item := range replacePathsPlaceholders(dirs, replacer) { if err = conn.CheckParentDirs(path.Dir(item)); err != nil { return fmt.Errorf("unable to check parent dirs for %q, user %q: %w", item, user.Username, err) } @@ -1389,8 +1393,7 @@ func executeExistFsActionForUser(exist []string, replacer *strings.Replacer, return fmt.Errorf("existence check error, unable to check root fs for user %q: %w", user.Username, err) } conn := NewBaseConnection(connectionID, protocolEventAction, "", "", user) - for _, item := range exist { - item = util.CleanPath(replaceWithReplacer(item, replacer)) + for _, item := range replacePathsPlaceholders(exist, replacer) { if _, err = conn.DoStat(item, 0, false); err != nil { return fmt.Errorf("error checking existence for path %q, user %q: %w", item, user.Username, err) } diff --git a/internal/common/eventmanager_test.go b/internal/common/eventmanager_test.go index 0f32434f..56815901 100644 --- a/internal/common/eventmanager_test.go +++ b/internal/common/eventmanager_test.go @@ -1598,6 +1598,16 @@ func TestWriteHTTPPartsError(t *testing.T) { assert.ErrorIs(t, err, io.ErrUnexpectedEOF) } +func TestReplacePathsPlaceholders(t *testing.T) { + replacer := strings.NewReplacer("{{VirtualPath}}", "/path1") + paths := []string{"{{VirtualPath}}", "/path1"} + paths = replacePathsPlaceholders(paths, replacer) + assert.Equal(t, []string{"/path1"}, paths) + paths = []string{"{{VirtualPath}}", "/path2"} + paths = replacePathsPlaceholders(paths, replacer) + assert.Equal(t, []string{"/path1", "/path2"}, paths) +} + func getErrorString(err error) string { if err == nil { return "" diff --git a/internal/dataprovider/eventrule.go b/internal/dataprovider/eventrule.go index ae5b251e..e6f4ed5e 100644 --- a/internal/dataprovider/eventrule.go +++ b/internal/dataprovider/eventrule.go @@ -1077,8 +1077,8 @@ func (f *ConditionOptions) validate() error { } if f.MinFileSize > 0 && f.MaxFileSize > 0 { if f.MaxFileSize <= f.MinFileSize { - return util.NewValidationError(fmt.Sprintf("invalid max file size %d, it is lesser or equal than min file size %d", - f.MaxFileSize, f.MinFileSize)) + return util.NewValidationError(fmt.Sprintf("invalid max file size %s, it is lesser or equal than min file size %s", + util.ByteCountSI(f.MaxFileSize), util.ByteCountSI(f.MinFileSize))) } } if config.IsShared == 0 { diff --git a/internal/httpd/webadmin.go b/internal/httpd/webadmin.go index d6467fb2..66207f30 100644 --- a/internal/httpd/webadmin.go +++ b/internal/httpd/webadmin.go @@ -496,7 +496,7 @@ func loadAdminTemplates(templatesPath string) { foldersTmpl := util.LoadTemplate(nil, foldersPaths...) folderTmpl := util.LoadTemplate(fsBaseTpl, folderPaths...) eventRulesTmpl := util.LoadTemplate(nil, eventRulesPaths...) - eventRuleTmpl := util.LoadTemplate(nil, eventRulePaths...) + eventRuleTmpl := util.LoadTemplate(fsBaseTpl, eventRulePaths...) eventActionsTmpl := util.LoadTemplate(nil, eventActionsPaths...) eventActionTmpl := util.LoadTemplate(nil, eventActionPaths...) statusTmpl := util.LoadTemplate(nil, statusPaths...) @@ -2138,11 +2138,11 @@ func getEventRuleConditionsFromPostFields(r *http.Request) (dataprovider.EventCo } } } - minFileSize, err := strconv.ParseInt(r.Form.Get("fs_min_size"), 10, 64) + minFileSize, err := util.ParseBytes(r.Form.Get("fs_min_size")) if err != nil { return dataprovider.EventConditions{}, fmt.Errorf("invalid min file size: %w", err) } - maxFileSize, err := strconv.ParseInt(r.Form.Get("fs_max_size"), 10, 64) + maxFileSize, err := util.ParseBytes(r.Form.Get("fs_max_size")) if err != nil { return dataprovider.EventConditions{}, fmt.Errorf("invalid max file size: %w", err) } diff --git a/templates/webadmin/eventrule.html b/templates/webadmin/eventrule.html index d2c8ecd3..7e45da38 100644 --- a/templates/webadmin/eventrule.html +++ b/templates/webadmin/eventrule.html @@ -347,20 +347,20 @@ along with this program. If not, see .
- File size limits. 0 means no limit + File size limits. 0 means no limit. You can use MB/GB suffix
- +
- +