mirror of
https://github.com/drakkan/sftpgo.git
synced 2024-11-21 23:20:24 +00:00
WebAdmin and REST API: remove too granular permissions
Our permissions system for admin users is too granular and some permissions overlap. For example, you can define an administrator with the "manage_system" permission and not with the "manage_admins" or "manage_user" permission, but the "manage_system" permission allows you to restore a backup and then create users and administrators. The following permissions will be removed: "manage_admins", "manage_apikeys", "manage_system", "retention_checks", "manage_event_rules", "manage_roles", "manage_ip_lists". Now you need to add the "*" permission to replace the removed granular permissions because the removed permissions allow actions that should only be allowed to super administrators. There is no point in having separate, overlapping permissions. Signed-off-by: Nicola Murino <nicola.murino@gmail.com>
This commit is contained in:
parent
65e8e2c1d4
commit
d0f348a46a
15 changed files with 127 additions and 162 deletions
|
@ -44,19 +44,12 @@ const (
|
||||||
PermAdminViewConnections = "view_conns"
|
PermAdminViewConnections = "view_conns"
|
||||||
PermAdminCloseConnections = "close_conns"
|
PermAdminCloseConnections = "close_conns"
|
||||||
PermAdminViewServerStatus = "view_status"
|
PermAdminViewServerStatus = "view_status"
|
||||||
PermAdminManageAdmins = "manage_admins"
|
|
||||||
PermAdminManageGroups = "manage_groups"
|
PermAdminManageGroups = "manage_groups"
|
||||||
PermAdminManageFolders = "manage_folders"
|
PermAdminManageFolders = "manage_folders"
|
||||||
PermAdminManageAPIKeys = "manage_apikeys"
|
|
||||||
PermAdminQuotaScans = "quota_scans"
|
PermAdminQuotaScans = "quota_scans"
|
||||||
PermAdminManageSystem = "manage_system"
|
|
||||||
PermAdminManageDefender = "manage_defender"
|
PermAdminManageDefender = "manage_defender"
|
||||||
PermAdminViewDefender = "view_defender"
|
PermAdminViewDefender = "view_defender"
|
||||||
PermAdminRetentionChecks = "retention_checks"
|
|
||||||
PermAdminViewEvents = "view_events"
|
PermAdminViewEvents = "view_events"
|
||||||
PermAdminManageEventRules = "manage_event_rules"
|
|
||||||
PermAdminManageRoles = "manage_roles"
|
|
||||||
PermAdminManageIPLists = "manage_ip_lists"
|
|
||||||
PermAdminDisableMFA = "disable_mfa"
|
PermAdminDisableMFA = "disable_mfa"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -72,12 +65,9 @@ const (
|
||||||
var (
|
var (
|
||||||
validAdminPerms = []string{PermAdminAny, PermAdminAddUsers, PermAdminChangeUsers, PermAdminDeleteUsers,
|
validAdminPerms = []string{PermAdminAny, PermAdminAddUsers, PermAdminChangeUsers, PermAdminDeleteUsers,
|
||||||
PermAdminViewUsers, PermAdminManageFolders, PermAdminManageGroups, PermAdminViewConnections,
|
PermAdminViewUsers, PermAdminManageFolders, PermAdminManageGroups, PermAdminViewConnections,
|
||||||
PermAdminCloseConnections, PermAdminViewServerStatus, PermAdminManageAdmins, PermAdminManageRoles,
|
PermAdminCloseConnections, PermAdminViewServerStatus, PermAdminQuotaScans,
|
||||||
PermAdminManageEventRules, PermAdminManageAPIKeys, PermAdminQuotaScans, PermAdminManageSystem,
|
PermAdminManageDefender, PermAdminViewDefender, PermAdminViewEvents, PermAdminDisableMFA}
|
||||||
PermAdminManageDefender, PermAdminViewDefender, PermAdminManageIPLists, PermAdminRetentionChecks,
|
forbiddenPermsForRoleAdmins = []string{PermAdminAny}
|
||||||
PermAdminViewEvents, PermAdminDisableMFA}
|
|
||||||
forbiddenPermsForRoleAdmins = []string{PermAdminAny, PermAdminManageAdmins, PermAdminManageSystem,
|
|
||||||
PermAdminManageEventRules, PermAdminManageIPLists, PermAdminManageRoles}
|
|
||||||
)
|
)
|
||||||
|
|
||||||
// AdminTOTPConfig defines the time-based one time password configuration
|
// AdminTOTPConfig defines the time-based one time password configuration
|
||||||
|
@ -265,12 +255,7 @@ type Admin struct {
|
||||||
// Last login as unix timestamp in milliseconds
|
// Last login as unix timestamp in milliseconds
|
||||||
LastLogin int64 `json:"last_login"`
|
LastLogin int64 `json:"last_login"`
|
||||||
// Role name. If set the admin can only administer users with the same role.
|
// Role name. If set the admin can only administer users with the same role.
|
||||||
// Role admins cannot have the following permissions:
|
// Role admins cannot be super administrators
|
||||||
// - manage_admins
|
|
||||||
// - manage_apikeys
|
|
||||||
// - manage_system
|
|
||||||
// - manage_event_rules
|
|
||||||
// - manage_roles
|
|
||||||
Role string `json:"role,omitempty"`
|
Role string `json:"role,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -346,13 +331,9 @@ func (a *Admin) validatePermissions() error {
|
||||||
}
|
}
|
||||||
if a.Role != "" {
|
if a.Role != "" {
|
||||||
if util.Contains(forbiddenPermsForRoleAdmins, perm) {
|
if util.Contains(forbiddenPermsForRoleAdmins, perm) {
|
||||||
deniedPerms := strings.Join(forbiddenPermsForRoleAdmins, ",")
|
|
||||||
return util.NewI18nError(
|
return util.NewI18nError(
|
||||||
util.NewValidationError(fmt.Sprintf("a role admin cannot have the following permissions: %q", deniedPerms)),
|
util.NewValidationError("a role admin cannot be a super admin"),
|
||||||
util.I18nErrorRoleAdminPerms,
|
util.I18nErrorRoleAdminPerms,
|
||||||
util.I18nErrorArgs(map[string]any{
|
|
||||||
"val": deniedPerms,
|
|
||||||
}),
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -922,7 +922,7 @@ func getProtocolFromRequest(r *http.Request) string {
|
||||||
}
|
}
|
||||||
|
|
||||||
func hideConfidentialData(claims *jwtTokenClaims, r *http.Request) bool {
|
func hideConfidentialData(claims *jwtTokenClaims, r *http.Request) bool {
|
||||||
if !claims.hasPerm(dataprovider.PermAdminManageSystem) {
|
if !claims.hasPerm(dataprovider.PermAdminAny) {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
return r.URL.Query().Get("confidential_data") != "1"
|
return r.URL.Query().Get("confidential_data") != "1"
|
||||||
|
|
|
@ -716,7 +716,7 @@ func TestRoleRelations(t *testing.T) {
|
||||||
a.Role = role.Name
|
a.Role = role.Name
|
||||||
_, resp, err = httpdtest.AddAdmin(a, http.StatusBadRequest)
|
_, resp, err = httpdtest.AddAdmin(a, http.StatusBadRequest)
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
assert.Contains(t, string(resp), "a role admin cannot have the following permissions")
|
assert.Contains(t, string(resp), "a role admin cannot be a super admin")
|
||||||
|
|
||||||
a.Permissions = []string{dataprovider.PermAdminAddUsers, dataprovider.PermAdminChangeUsers,
|
a.Permissions = []string{dataprovider.PermAdminAddUsers, dataprovider.PermAdminChangeUsers,
|
||||||
dataprovider.PermAdminDeleteUsers, dataprovider.PermAdminViewUsers}
|
dataprovider.PermAdminDeleteUsers, dataprovider.PermAdminViewUsers}
|
||||||
|
@ -11625,7 +11625,7 @@ func TestUpdateAdminMock(t *testing.T) {
|
||||||
assert.Error(t, err)
|
assert.Error(t, err)
|
||||||
admin := getTestAdmin()
|
admin := getTestAdmin()
|
||||||
admin.Username = altAdminUsername
|
admin.Username = altAdminUsername
|
||||||
admin.Permissions = []string{dataprovider.PermAdminManageAdmins}
|
admin.Permissions = []string{dataprovider.PermAdminAny}
|
||||||
asJSON, err := json.Marshal(admin)
|
asJSON, err := json.Marshal(admin)
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
req, _ := http.NewRequest(http.MethodPost, adminPath, bytes.NewBuffer(asJSON))
|
req, _ := http.NewRequest(http.MethodPost, adminPath, bytes.NewBuffer(asJSON))
|
||||||
|
@ -11682,7 +11682,7 @@ func TestUpdateAdminMock(t *testing.T) {
|
||||||
altToken, err := getJWTAPITokenFromTestServer(altAdminUsername, defaultTokenAuthPass)
|
altToken, err := getJWTAPITokenFromTestServer(altAdminUsername, defaultTokenAuthPass)
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
admin.Password = "" // it must remain unchanged
|
admin.Password = "" // it must remain unchanged
|
||||||
admin.Permissions = []string{dataprovider.PermAdminManageAdmins}
|
admin.Permissions = []string{dataprovider.PermAdminAny}
|
||||||
asJSON, err = json.Marshal(admin)
|
asJSON, err = json.Marshal(admin)
|
||||||
assert.NoError(t, err)
|
assert.NoError(t, err)
|
||||||
req, _ = http.NewRequest(http.MethodPut, path.Join(adminPath, altAdminUsername), bytes.NewBuffer(asJSON))
|
req, _ = http.NewRequest(http.MethodPut, path.Join(adminPath, altAdminUsername), bytes.NewBuffer(asJSON))
|
||||||
|
|
|
@ -1333,15 +1333,15 @@ func (s *httpdServer) initializeRouter() {
|
||||||
router.With(forbidAPIKeyAuthentication).Get(admin2FARecoveryCodesPath, getRecoveryCodes)
|
router.With(forbidAPIKeyAuthentication).Get(admin2FARecoveryCodesPath, getRecoveryCodes)
|
||||||
router.With(forbidAPIKeyAuthentication).Post(admin2FARecoveryCodesPath, generateRecoveryCodes)
|
router.With(forbidAPIKeyAuthentication).Post(admin2FARecoveryCodesPath, generateRecoveryCodes)
|
||||||
|
|
||||||
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminManageAPIKeys)).
|
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminAny)).
|
||||||
Get(apiKeysPath, getAPIKeys)
|
Get(apiKeysPath, getAPIKeys)
|
||||||
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminManageAPIKeys)).
|
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminAny)).
|
||||||
Post(apiKeysPath, addAPIKey)
|
Post(apiKeysPath, addAPIKey)
|
||||||
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminManageAPIKeys)).
|
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminAny)).
|
||||||
Get(apiKeysPath+"/{id}", getAPIKeyByID)
|
Get(apiKeysPath+"/{id}", getAPIKeyByID)
|
||||||
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminManageAPIKeys)).
|
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminAny)).
|
||||||
Put(apiKeysPath+"/{id}", updateAPIKey)
|
Put(apiKeysPath+"/{id}", updateAPIKey)
|
||||||
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminManageAPIKeys)).
|
router.With(forbidAPIKeyAuthentication, s.checkPerm(dataprovider.PermAdminAny)).
|
||||||
Delete(apiKeysPath+"/{id}", deleteAPIKey)
|
Delete(apiKeysPath+"/{id}", deleteAPIKey)
|
||||||
|
|
||||||
router.Group(func(router chi.Router) {
|
router.Group(func(router chi.Router) {
|
||||||
|
@ -1376,9 +1376,9 @@ func (s *httpdServer) initializeRouter() {
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageGroups)).Post(groupPath, addGroup)
|
router.With(s.checkPerm(dataprovider.PermAdminManageGroups)).Post(groupPath, addGroup)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageGroups)).Put(groupPath+"/{name}", updateGroup)
|
router.With(s.checkPerm(dataprovider.PermAdminManageGroups)).Put(groupPath+"/{name}", updateGroup)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageGroups)).Delete(groupPath+"/{name}", deleteGroup)
|
router.With(s.checkPerm(dataprovider.PermAdminManageGroups)).Delete(groupPath+"/{name}", deleteGroup)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Get(dumpDataPath, dumpData)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(dumpDataPath, dumpData)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Get(loadDataPath, loadData)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(loadDataPath, loadData)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Post(loadDataPath, loadDataFromRequest)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(loadDataPath, loadDataFromRequest)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminChangeUsers)).Put(quotasBasePath+"/users/{username}/usage",
|
router.With(s.checkPerm(dataprovider.PermAdminChangeUsers)).Put(quotasBasePath+"/users/{username}/usage",
|
||||||
updateUserQuotaUsage)
|
updateUserQuotaUsage)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminChangeUsers)).Put(quotasBasePath+"/users/{username}/transfer-usage",
|
router.With(s.checkPerm(dataprovider.PermAdminChangeUsers)).Put(quotasBasePath+"/users/{username}/transfer-usage",
|
||||||
|
@ -1388,14 +1388,14 @@ func (s *httpdServer) initializeRouter() {
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(defenderHosts, getDefenderHosts)
|
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(defenderHosts, getDefenderHosts)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(defenderHosts+"/{id}", getDefenderHostByID)
|
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(defenderHosts+"/{id}", getDefenderHostByID)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageDefender)).Delete(defenderHosts+"/{id}", deleteDefenderHostByID)
|
router.With(s.checkPerm(dataprovider.PermAdminManageDefender)).Delete(defenderHosts+"/{id}", deleteDefenderHostByID)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins)).Get(adminPath, getAdmins)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(adminPath, getAdmins)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins)).Post(adminPath, addAdmin)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(adminPath, addAdmin)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins)).Get(adminPath+"/{username}", getAdminByUsername)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(adminPath+"/{username}", getAdminByUsername)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins)).Put(adminPath+"/{username}", updateAdmin)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Put(adminPath+"/{username}", updateAdmin)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins)).Delete(adminPath+"/{username}", deleteAdmin)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Delete(adminPath+"/{username}", deleteAdmin)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminDisableMFA)).Put(adminPath+"/{username}/2fa/disable", disableAdmin2FA)
|
router.With(s.checkPerm(dataprovider.PermAdminDisableMFA)).Put(adminPath+"/{username}/2fa/disable", disableAdmin2FA)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminRetentionChecks)).Get(retentionChecksPath, getRetentionChecks)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(retentionChecksPath, getRetentionChecks)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminRetentionChecks)).Post(retentionBasePath+"/{username}/check",
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(retentionBasePath+"/{username}/check",
|
||||||
startRetentionCheck)
|
startRetentionCheck)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), compressor.Handler).
|
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), compressor.Handler).
|
||||||
Get(fsEventsPath, searchFsEvents)
|
Get(fsEventsPath, searchFsEvents)
|
||||||
|
@ -1403,27 +1403,27 @@ func (s *httpdServer) initializeRouter() {
|
||||||
Get(providerEventsPath, searchProviderEvents)
|
Get(providerEventsPath, searchProviderEvents)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), compressor.Handler).
|
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), compressor.Handler).
|
||||||
Get(logEventsPath, searchLogEvents)
|
Get(logEventsPath, searchLogEvents)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Get(eventActionsPath, getEventActions)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(eventActionsPath, getEventActions)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Get(eventActionsPath+"/{name}", getEventActionByName)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(eventActionsPath+"/{name}", getEventActionByName)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Post(eventActionsPath, addEventAction)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(eventActionsPath, addEventAction)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Put(eventActionsPath+"/{name}", updateEventAction)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Put(eventActionsPath+"/{name}", updateEventAction)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Delete(eventActionsPath+"/{name}", deleteEventAction)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Delete(eventActionsPath+"/{name}", deleteEventAction)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Get(eventRulesPath, getEventRules)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(eventRulesPath, getEventRules)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Get(eventRulesPath+"/{name}", getEventRuleByName)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(eventRulesPath+"/{name}", getEventRuleByName)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Post(eventRulesPath, addEventRule)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(eventRulesPath, addEventRule)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Put(eventRulesPath+"/{name}", updateEventRule)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Put(eventRulesPath+"/{name}", updateEventRule)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Delete(eventRulesPath+"/{name}", deleteEventRule)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Delete(eventRulesPath+"/{name}", deleteEventRule)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Post(eventRulesPath+"/run/{name}", runOnDemandRule)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(eventRulesPath+"/run/{name}", runOnDemandRule)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles)).Get(rolesPath, getRoles)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(rolesPath, getRoles)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles)).Post(rolesPath, addRole)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(rolesPath, addRole)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles)).Get(rolesPath+"/{name}", getRoleByName)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(rolesPath+"/{name}", getRoleByName)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles)).Put(rolesPath+"/{name}", updateRole)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Put(rolesPath+"/{name}", updateRole)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles)).Delete(rolesPath+"/{name}", deleteRole)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Delete(rolesPath+"/{name}", deleteRole)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists), compressor.Handler).Get(ipListsPath+"/{type}", getIPListEntries) //nolint:goconst
|
router.With(s.checkPerm(dataprovider.PermAdminAny), compressor.Handler).Get(ipListsPath+"/{type}", getIPListEntries) //nolint:goconst
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists)).Post(ipListsPath+"/{type}", addIPListEntry)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(ipListsPath+"/{type}", addIPListEntry)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists)).Get(ipListsPath+"/{type}/{ipornet}", getIPListEntry) //nolint:goconst
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(ipListsPath+"/{type}/{ipornet}", getIPListEntry) //nolint:goconst
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists)).Put(ipListsPath+"/{type}/{ipornet}", updateIPListEntry)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Put(ipListsPath+"/{type}/{ipornet}", updateIPListEntry)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists)).Delete(ipListsPath+"/{type}/{ipornet}", deleteIPListEntry)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Delete(ipListsPath+"/{type}/{ipornet}", deleteIPListEntry)
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
@ -1744,18 +1744,18 @@ func (s *httpdServer) setupWebAdminRoutes() {
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageFolders)).Post(webFolderPath, s.handleWebAddFolderPost)
|
router.With(s.checkPerm(dataprovider.PermAdminManageFolders)).Post(webFolderPath, s.handleWebAddFolderPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewServerStatus), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminViewServerStatus), s.refreshCookie).
|
||||||
Get(webStatusPath, s.handleWebGetStatus)
|
Get(webStatusPath, s.handleWebGetStatus)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminsPath, s.handleGetWebAdmins)
|
Get(webAdminsPath, s.handleGetWebAdmins)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins), compressor.Handler, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), compressor.Handler, s.refreshCookie).
|
||||||
Get(webAdminsPath+jsonAPISuffix, getAllAdmins)
|
Get(webAdminsPath+jsonAPISuffix, getAllAdmins)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminPath, s.handleWebAddAdminGet)
|
Get(webAdminPath, s.handleWebAddAdminGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminPath+"/{username}", s.handleWebUpdateAdminGet)
|
Get(webAdminPath+"/{username}", s.handleWebUpdateAdminGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins)).Post(webAdminPath, s.handleWebAddAdminPost)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminPath, s.handleWebAddAdminPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins)).Post(webAdminPath+"/{username}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminPath+"/{username}",
|
||||||
s.handleWebUpdateAdminPost)
|
s.handleWebUpdateAdminPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageAdmins), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader).
|
||||||
Delete(webAdminPath+"/{username}", deleteAdmin)
|
Delete(webAdminPath+"/{username}", deleteAdmin)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminDisableMFA), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminDisableMFA), verifyCSRFHeader).
|
||||||
Put(webAdminPath+"/{username}/2fa/disable", disableAdmin2FA)
|
Put(webAdminPath+"/{username}/2fa/disable", disableAdmin2FA)
|
||||||
|
@ -1775,61 +1775,61 @@ func (s *httpdServer) setupWebAdminRoutes() {
|
||||||
Put(webUserPath+"/{username}/2fa/disable", disableUser2FA)
|
Put(webUserPath+"/{username}/2fa/disable", disableUser2FA)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminQuotaScans), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminQuotaScans), verifyCSRFHeader).
|
||||||
Post(webQuotaScanPath+"/{username}", startUserQuotaScan)
|
Post(webQuotaScanPath+"/{username}", startUserQuotaScan)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Get(webMaintenancePath, s.handleWebMaintenance)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(webMaintenancePath, s.handleWebMaintenance)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Get(webBackupPath, dumpData)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(webBackupPath, dumpData)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Post(webRestorePath, s.handleWebRestore)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webRestorePath, s.handleWebRestore)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webTemplateUser, s.handleWebTemplateUserGet)
|
Get(webTemplateUser, s.handleWebTemplateUserGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Post(webTemplateUser, s.handleWebTemplateUserPost)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webTemplateUser, s.handleWebTemplateUserPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webTemplateFolder, s.handleWebTemplateFolderGet)
|
Get(webTemplateFolder, s.handleWebTemplateFolderGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Post(webTemplateFolder, s.handleWebTemplateFolderPost)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webTemplateFolder, s.handleWebTemplateFolderPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(webDefenderPath, s.handleWebDefenderPage)
|
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(webDefenderPath, s.handleWebDefenderPage)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(webDefenderHostsPath, getDefenderHosts)
|
router.With(s.checkPerm(dataprovider.PermAdminViewDefender)).Get(webDefenderHostsPath, getDefenderHosts)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageDefender), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminManageDefender), verifyCSRFHeader).
|
||||||
Delete(webDefenderHostsPath+"/{id}", deleteDefenderHostByID)
|
Delete(webDefenderHostsPath+"/{id}", deleteDefenderHostByID)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), compressor.Handler, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), compressor.Handler, s.refreshCookie).
|
||||||
Get(webAdminEventActionsPath+jsonAPISuffix, getAllActions)
|
Get(webAdminEventActionsPath+jsonAPISuffix, getAllActions)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminEventActionsPath, s.handleWebGetEventActions)
|
Get(webAdminEventActionsPath, s.handleWebGetEventActions)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminEventActionPath, s.handleWebAddEventActionGet)
|
Get(webAdminEventActionPath, s.handleWebAddEventActionGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Post(webAdminEventActionPath,
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminEventActionPath,
|
||||||
s.handleWebAddEventActionPost)
|
s.handleWebAddEventActionPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminEventActionPath+"/{name}", s.handleWebUpdateEventActionGet)
|
Get(webAdminEventActionPath+"/{name}", s.handleWebUpdateEventActionGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Post(webAdminEventActionPath+"/{name}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminEventActionPath+"/{name}",
|
||||||
s.handleWebUpdateEventActionPost)
|
s.handleWebUpdateEventActionPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader).
|
||||||
Delete(webAdminEventActionPath+"/{name}", deleteEventAction)
|
Delete(webAdminEventActionPath+"/{name}", deleteEventAction)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), compressor.Handler, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), compressor.Handler, s.refreshCookie).
|
||||||
Get(webAdminEventRulesPath+jsonAPISuffix, getAllRules)
|
Get(webAdminEventRulesPath+jsonAPISuffix, getAllRules)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminEventRulesPath, s.handleWebGetEventRules)
|
Get(webAdminEventRulesPath, s.handleWebGetEventRules)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminEventRulePath, s.handleWebAddEventRuleGet)
|
Get(webAdminEventRulePath, s.handleWebAddEventRuleGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Post(webAdminEventRulePath,
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminEventRulePath,
|
||||||
s.handleWebAddEventRulePost)
|
s.handleWebAddEventRulePost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminEventRulePath+"/{name}", s.handleWebUpdateEventRuleGet)
|
Get(webAdminEventRulePath+"/{name}", s.handleWebUpdateEventRuleGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules)).Post(webAdminEventRulePath+"/{name}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminEventRulePath+"/{name}",
|
||||||
s.handleWebUpdateEventRulePost)
|
s.handleWebUpdateEventRulePost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader).
|
||||||
Delete(webAdminEventRulePath+"/{name}", deleteEventRule)
|
Delete(webAdminEventRulePath+"/{name}", deleteEventRule)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageEventRules), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader).
|
||||||
Post(webAdminEventRulePath+"/run/{name}", runOnDemandRule)
|
Post(webAdminEventRulePath+"/run/{name}", runOnDemandRule)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminRolesPath, s.handleWebGetRoles)
|
Get(webAdminRolesPath, s.handleWebGetRoles)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles), compressor.Handler, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), compressor.Handler, s.refreshCookie).
|
||||||
Get(webAdminRolesPath+jsonAPISuffix, getAllRoles)
|
Get(webAdminRolesPath+jsonAPISuffix, getAllRoles)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminRolePath, s.handleWebAddRoleGet)
|
Get(webAdminRolePath, s.handleWebAddRoleGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles)).Post(webAdminRolePath, s.handleWebAddRolePost)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminRolePath, s.handleWebAddRolePost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles), s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).
|
||||||
Get(webAdminRolePath+"/{name}", s.handleWebUpdateRoleGet)
|
Get(webAdminRolePath+"/{name}", s.handleWebUpdateRoleGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles)).Post(webAdminRolePath+"/{name}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webAdminRolePath+"/{name}",
|
||||||
s.handleWebUpdateRolePost)
|
s.handleWebUpdateRolePost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageRoles), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader).
|
||||||
Delete(webAdminRolePath+"/{name}", deleteRole)
|
Delete(webAdminRolePath+"/{name}", deleteRole)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), s.refreshCookie).Get(webEventsPath,
|
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), s.refreshCookie).Get(webEventsPath,
|
||||||
s.handleWebGetEvents)
|
s.handleWebGetEvents)
|
||||||
|
@ -1839,24 +1839,24 @@ func (s *httpdServer) setupWebAdminRoutes() {
|
||||||
Get(webEventsProviderSearchPath, searchProviderEvents)
|
Get(webEventsProviderSearchPath, searchProviderEvents)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), compressor.Handler, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminViewEvents), compressor.Handler, s.refreshCookie).
|
||||||
Get(webEventsLogSearchPath, searchLogEvents)
|
Get(webEventsLogSearchPath, searchLogEvents)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists)).Get(webIPListsPath, s.handleWebIPListsPage)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Get(webIPListsPath, s.handleWebIPListsPage)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists), compressor.Handler, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), compressor.Handler, s.refreshCookie).
|
||||||
Get(webIPListsPath+"/{type}", getIPListEntries)
|
Get(webIPListsPath+"/{type}", getIPListEntries)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists), s.refreshCookie).Get(webIPListPath+"/{type}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).Get(webIPListPath+"/{type}",
|
||||||
s.handleWebAddIPListEntryGet)
|
s.handleWebAddIPListEntryGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists)).Post(webIPListPath+"/{type}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webIPListPath+"/{type}",
|
||||||
s.handleWebAddIPListEntryPost)
|
s.handleWebAddIPListEntryPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists), s.refreshCookie).Get(webIPListPath+"/{type}/{ipornet}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).Get(webIPListPath+"/{type}/{ipornet}",
|
||||||
s.handleWebUpdateIPListEntryGet)
|
s.handleWebUpdateIPListEntryGet)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists)).Post(webIPListPath+"/{type}/{ipornet}",
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webIPListPath+"/{type}/{ipornet}",
|
||||||
s.handleWebUpdateIPListEntryPost)
|
s.handleWebUpdateIPListEntryPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageIPLists), verifyCSRFHeader).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader).
|
||||||
Delete(webIPListPath+"/{type}/{ipornet}", deleteIPListEntry)
|
Delete(webIPListPath+"/{type}/{ipornet}", deleteIPListEntry)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem), s.refreshCookie).Get(webConfigsPath, s.handleWebConfigs)
|
router.With(s.checkPerm(dataprovider.PermAdminAny), s.refreshCookie).Get(webConfigsPath, s.handleWebConfigs)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem)).Post(webConfigsPath, s.handleWebConfigsPost)
|
router.With(s.checkPerm(dataprovider.PermAdminAny)).Post(webConfigsPath, s.handleWebConfigsPost)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem), verifyCSRFHeader, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader, s.refreshCookie).
|
||||||
Post(webConfigsPath+"/smtp/test", testSMTPConfig)
|
Post(webConfigsPath+"/smtp/test", testSMTPConfig)
|
||||||
router.With(s.checkPerm(dataprovider.PermAdminManageSystem), verifyCSRFHeader, s.refreshCookie).
|
router.With(s.checkPerm(dataprovider.PermAdminAny), verifyCSRFHeader, s.refreshCookie).
|
||||||
Post(webOAuth2TokenPath, handleSMTPOAuth2TokenRequestPost)
|
Post(webOAuth2TokenPath, handleSMTPOAuth2TokenRequestPost)
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
|
@ -3270,7 +3270,7 @@ func (s *httpdServer) handleWebTemplateUserPost(w http.ResponseWriter, r *http.R
|
||||||
s.renderMessagePage(w, r, util.I18nTemplateUserTitle, http.StatusBadRequest, err, "")
|
s.renderMessagePage(w, r, util.I18nTemplateUserTitle, http.StatusBadRequest, err, "")
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
// to create a template the "manage_system" permission is required, so role admins cannot use
|
// to create a template the "*" permission is required, so role admins cannot use
|
||||||
// this method, we don't need to force the role
|
// this method, we don't need to force the role
|
||||||
dump.Users = append(dump.Users, u)
|
dump.Users = append(dump.Users, u)
|
||||||
for _, folder := range u.VirtualFolders {
|
for _, folder := range u.VirtualFolders {
|
||||||
|
|
|
@ -1517,7 +1517,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
requestBody:
|
requestBody:
|
||||||
required: true
|
required: true
|
||||||
content:
|
content:
|
||||||
|
@ -1565,7 +1565,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
responses:
|
responses:
|
||||||
'200':
|
'200':
|
||||||
description: successful operation
|
description: successful operation
|
||||||
|
@ -1709,7 +1709,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
requestBody:
|
requestBody:
|
||||||
required: true
|
required: true
|
||||||
content:
|
content:
|
||||||
|
@ -1757,7 +1757,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
responses:
|
responses:
|
||||||
'200':
|
'200':
|
||||||
description: successful operation
|
description: successful operation
|
||||||
|
@ -2081,7 +2081,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
requestBody:
|
requestBody:
|
||||||
required: true
|
required: true
|
||||||
content:
|
content:
|
||||||
|
@ -2129,7 +2129,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
responses:
|
responses:
|
||||||
'200':
|
'200':
|
||||||
description: successful operation
|
description: successful operation
|
||||||
|
@ -2273,7 +2273,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
requestBody:
|
requestBody:
|
||||||
required: true
|
required: true
|
||||||
content:
|
content:
|
||||||
|
@ -2321,7 +2321,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
responses:
|
responses:
|
||||||
'200':
|
'200':
|
||||||
description: successful operation
|
description: successful operation
|
||||||
|
@ -3416,7 +3416,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the hash of the password and the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the hash of the password and the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
requestBody:
|
requestBody:
|
||||||
required: true
|
required: true
|
||||||
content:
|
content:
|
||||||
|
@ -3464,7 +3464,7 @@ paths:
|
||||||
name: confidential_data
|
name: confidential_data
|
||||||
schema:
|
schema:
|
||||||
type: integer
|
type: integer
|
||||||
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the hash of the password and the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the manage_system permission is not granted.'
|
description: 'If set to 1 confidential data will not be hidden. This means that the response will contain the hash of the password and the key and additional data for secrets. If a master key is not set or an external KMS is used, the data returned are enough to get the secrets in cleartext. Ignored if the * permission is not granted.'
|
||||||
responses:
|
responses:
|
||||||
'200':
|
'200':
|
||||||
description: successful operation
|
description: successful operation
|
||||||
|
@ -4935,23 +4935,16 @@ components:
|
||||||
- view_conns
|
- view_conns
|
||||||
- close_conns
|
- close_conns
|
||||||
- view_status
|
- view_status
|
||||||
- manage_admins
|
|
||||||
- manage_folders
|
- manage_folders
|
||||||
- manage_groups
|
- manage_groups
|
||||||
- manage_apikeys
|
|
||||||
- quota_scans
|
- quota_scans
|
||||||
- manage_system
|
|
||||||
- manage_defender
|
- manage_defender
|
||||||
- view_defender
|
- view_defender
|
||||||
- retention_checks
|
|
||||||
- view_events
|
- view_events
|
||||||
- manage_event_rules
|
|
||||||
- manage_roles
|
|
||||||
- manage_ip_lists
|
|
||||||
- disable_mfa
|
- disable_mfa
|
||||||
description: |
|
description: |
|
||||||
Admin permissions:
|
Admin permissions:
|
||||||
* `*` - all permissions are granted
|
* `*` - super admin permissions are granted
|
||||||
* `add_users` - add new users is allowed
|
* `add_users` - add new users is allowed
|
||||||
* `edit_users` - change existing users is allowed
|
* `edit_users` - change existing users is allowed
|
||||||
* `del_users` - remove users is allowed
|
* `del_users` - remove users is allowed
|
||||||
|
@ -4959,19 +4952,12 @@ components:
|
||||||
* `view_conns` - list active connections is allowed
|
* `view_conns` - list active connections is allowed
|
||||||
* `close_conns` - close active connections is allowed
|
* `close_conns` - close active connections is allowed
|
||||||
* `view_status` - view the server status is allowed
|
* `view_status` - view the server status is allowed
|
||||||
* `manage_admins` - manage other admins is allowed
|
|
||||||
* `manage_folders` - manage folders is allowed
|
* `manage_folders` - manage folders is allowed
|
||||||
* `manage_groups` - manage groups is allowed
|
* `manage_groups` - manage groups is allowed
|
||||||
* `manage_apikeys` - manage API keys is allowed
|
|
||||||
* `quota_scans` - view and start quota scans is allowed
|
* `quota_scans` - view and start quota scans is allowed
|
||||||
* `manage_system` - backups and restores are allowed
|
|
||||||
* `manage_defender` - remove ip from the dynamic blocklist is allowed
|
* `manage_defender` - remove ip from the dynamic blocklist is allowed
|
||||||
* `view_defender` - list the dynamic blocklist is allowed
|
* `view_defender` - list the dynamic blocklist is allowed
|
||||||
* `retention_checks` - view and start retention checks is allowed
|
|
||||||
* `view_events` - view and search filesystem and provider events is allowed
|
* `view_events` - view and search filesystem and provider events is allowed
|
||||||
* `manage_event_rules` - manage event actions and rules is allowed
|
|
||||||
* `manage_roles` - manage roles is allowed
|
|
||||||
* `manage_ip_lists` - manage global and ratelimter allow lists and defender block and safe lists is allowed
|
|
||||||
* `disable_mfa` - allow to disable two-factor authentication for users and admins
|
* `disable_mfa` - allow to disable two-factor authentication for users and admins
|
||||||
FsProviders:
|
FsProviders:
|
||||||
type: integer
|
type: integer
|
||||||
|
@ -6111,7 +6097,7 @@ components:
|
||||||
description: Last user login as unix timestamp in milliseconds. It is saved at most once every 10 minutes
|
description: Last user login as unix timestamp in milliseconds. It is saved at most once every 10 minutes
|
||||||
role:
|
role:
|
||||||
type: string
|
type: string
|
||||||
description: 'If set the admin can only administer users with the same role. Role admins cannot have the following permissions: "manage_admins", "manage_apikeys", "manage_system", "manage_event_rules", "manage_roles", "manage_ip_lists"'
|
description: 'If set the admin can only administer users with the same role. Role admins cannot have the "*" permission'
|
||||||
AdminProfile:
|
AdminProfile:
|
||||||
type: object
|
type: object
|
||||||
properties:
|
properties:
|
||||||
|
|
|
@ -734,14 +734,14 @@
|
||||||
"access_time_help": "No restrictions means access is always allowed, the time must be set in the format HH:MM. Use UTC time"
|
"access_time_help": "No restrictions means access is always allowed, the time must be set in the format HH:MM. Use UTC time"
|
||||||
},
|
},
|
||||||
"admin": {
|
"admin": {
|
||||||
"role_permissions": "A role admin cannot have the following permissions: {{val}}",
|
"role_permissions": "A role admin cannot have the \"*\" permission",
|
||||||
"view_manage": "View and manage admins",
|
"view_manage": "View and manage admins",
|
||||||
"self_delete": "You cannot delete yourself",
|
"self_delete": "You cannot delete yourself",
|
||||||
"self_permissions": "You cannot change your permissions",
|
"self_permissions": "You cannot change your permissions",
|
||||||
"self_disable": "You cannot disable yourself",
|
"self_disable": "You cannot disable yourself",
|
||||||
"self_role": "You cannot add/change your role",
|
"self_role": "You cannot add/change your role",
|
||||||
"password_help": "If blank the current password will not be changed",
|
"password_help": "If blank the current password will not be changed",
|
||||||
"role_help": "Setting a role limit the administrator to only manage users with the same role. Administrators with a role cannot have the following permissions: \"manage_admins\", \"manage_roles\", \"manage_event_rules\", \"manage_apikeys\", \"manage_system\", \"manage_ip_lists\"",
|
"role_help": "Setting a role limit the administrator to only manage users with the same role. Administrators with a role cannot be super administrators",
|
||||||
"users_groups": "Groups for users",
|
"users_groups": "Groups for users",
|
||||||
"users_groups_help": "Groups automatically selected for new users created by this admin. The admin will still be able to choose different groups. These settings are only used for this admin UI and they will be ignored in REST API/hooks",
|
"users_groups_help": "Groups automatically selected for new users created by this admin. The admin will still be able to choose different groups. These settings are only used for this admin UI and they will be ignored in REST API/hooks",
|
||||||
"group_membership": "Add as membership",
|
"group_membership": "Add as membership",
|
||||||
|
|
|
@ -734,14 +734,14 @@
|
||||||
"access_time_help": "Nessuna restrizione significa che l'accesso è sempre consentito, l'ora deve essere impostata nel formato HH:MM. Utilizzare l'ora UTC"
|
"access_time_help": "Nessuna restrizione significa che l'accesso è sempre consentito, l'ora deve essere impostata nel formato HH:MM. Utilizzare l'ora UTC"
|
||||||
},
|
},
|
||||||
"admin": {
|
"admin": {
|
||||||
"role_permissions": "Un amministratore di ruolo non può avere le seguenti autorizzazioni: {{val}}",
|
"role_permissions": "Un amministratore di ruolo non può avere il permesso \"*\"",
|
||||||
"view_manage": "Visualizza e gestisci amministratori",
|
"view_manage": "Visualizza e gestisci amministratori",
|
||||||
"self_delete": "Non puoi eliminare te stesso",
|
"self_delete": "Non puoi eliminare te stesso",
|
||||||
"self_permissions": "Non puoi cambiare i tuoi permessi",
|
"self_permissions": "Non puoi cambiare i tuoi permessi",
|
||||||
"self_disable": "Non puoi disabilitare te stesso",
|
"self_disable": "Non puoi disabilitare te stesso",
|
||||||
"self_role": "Non puoi aggiungere/modificare il tuo ruolo",
|
"self_role": "Non puoi aggiungere/modificare il tuo ruolo",
|
||||||
"password_help": "Se vuoto la password corrente non verrà modificata",
|
"password_help": "Se vuoto la password corrente non verrà modificata",
|
||||||
"role_help": "L'impostazione di un ruolo limita l'amministratore a gestire solo gli utenti con lo stesso ruolo. Gli amministratori con un ruolo non possono avere le seguenti autorizzazioni: \"manage_admins\", \"manage_roles\", \"manage_event_rules\", \"manage_apikeys\", \"manage_system\", \"manage_ip_lists\"",
|
"role_help": "L'impostazione di un ruolo limita l'amministratore a gestire solo gli utenti con lo stesso ruolo. Gli amministratori con un ruolo non possono essere super amministratori",
|
||||||
"users_groups": "Gruppi per gli utenti",
|
"users_groups": "Gruppi per gli utenti",
|
||||||
"users_groups_help": "Gruppi selezionati automaticamente per i nuovi utenti creati da questo amministratore. L'amministratore potrà comunque scegliere gruppi differenti. Queste impostazioni vengono utilizzate solo per questa interfaccia utente di amministrazione e verranno ignorate negli hook/API REST",
|
"users_groups_help": "Gruppi selezionati automaticamente per i nuovi utenti creati da questo amministratore. L'amministratore potrà comunque scegliere gruppi differenti. Queste impostazioni vengono utilizzate solo per questa interfaccia utente di amministrazione e verranno ignorate negli hook/API REST",
|
||||||
"group_membership": "Aggiungi come di appartenenza",
|
"group_membership": "Aggiungi come di appartenenza",
|
||||||
|
|
|
@ -81,7 +81,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</label>
|
</label>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{- if .LoggedUser.HasPermission "manage_admins"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<a href="{{.AdminURL}}" class="btn btn-primary ms-5">
|
<a href="{{.AdminURL}}" class="btn btn-primary ms-5">
|
||||||
<i class="ki-duotone ki-plus fs-2"></i>
|
<i class="ki-duotone ki-plus fs-2"></i>
|
||||||
<span data-i18n="general.add">Add</span>
|
<span data-i18n="general.add">Add</span>
|
||||||
|
@ -356,7 +356,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
<i class="ki-duotone ki-down fs-5 ms-1 rotate-180"></i>
|
<i class="ki-duotone ki-down fs-5 ms-1 rotate-180"></i>
|
||||||
</button>
|
</button>
|
||||||
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
||||||
//{{- if .LoggedUser.HasPermission "manage_admins"}}
|
//{{- if .LoggedUser.HasPermission "*"}}
|
||||||
numActions++;
|
numActions++;
|
||||||
actions+=`<div class="menu-item px-3">
|
actions+=`<div class="menu-item px-3">
|
||||||
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
||||||
|
@ -370,7 +370,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</div>`;
|
</div>`;
|
||||||
}
|
}
|
||||||
//{{- end}}
|
//{{- end}}
|
||||||
//{{- if .LoggedUser.HasPermission "manage_admins"}}
|
//{{- if .LoggedUser.HasPermission "*"}}
|
||||||
if (username != row.username){
|
if (username != row.username){
|
||||||
numActions++;
|
numActions++;
|
||||||
actions+=`<div class="menu-item px-3">
|
actions+=`<div class="menu-item px-3">
|
||||||
|
|
|
@ -126,7 +126,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
{{- end}}
|
{{- end}}
|
||||||
{{ if .LoggedUser.HasPermission "manage_event_rules"}}
|
{{ if .LoggedUser.HasPermission "*"}}
|
||||||
<div data-kt-menu-trigger="click" class="menu-item menu-accordion {{- if .IsEventManagerPage}} here show{{- end}}">
|
<div data-kt-menu-trigger="click" class="menu-item menu-accordion {{- if .IsEventManagerPage}} here show{{- end}}">
|
||||||
<span class="menu-link">
|
<span class="menu-link">
|
||||||
<span class="menu-icon">
|
<span class="menu-icon">
|
||||||
|
@ -158,7 +158,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{- end}}
|
{{- end}}
|
||||||
{{- if or (.LoggedUser.HasPermission "manage_ip_lists") (and .HasDefender (.LoggedUser.HasPermission "view_defender"))}}
|
{{- if or (.LoggedUser.HasPermission "*") (and .HasDefender (.LoggedUser.HasPermission "view_defender"))}}
|
||||||
<div data-kt-menu-trigger="click" class="menu-item menu-accordion {{- if .IsIPManagerPage}} here show{{- end}}">
|
<div data-kt-menu-trigger="click" class="menu-item menu-accordion {{- if .IsIPManagerPage}} here show{{- end}}">
|
||||||
<span class="menu-link">
|
<span class="menu-link">
|
||||||
<span class="menu-icon">
|
<span class="menu-icon">
|
||||||
|
@ -168,7 +168,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
<span class="menu-arrow"></span>
|
<span class="menu-arrow"></span>
|
||||||
</span>
|
</span>
|
||||||
<div class="menu-sub menu-sub-accordion">
|
<div class="menu-sub menu-sub-accordion">
|
||||||
{{- if .LoggedUser.HasPermission "manage_ip_lists"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<div class="menu-item">
|
<div class="menu-item">
|
||||||
<a class="menu-link {{- if eq .CurrentURL .IPListsURL}} active{{- end}}" href="{{.IPListsURL}}">
|
<a class="menu-link {{- if eq .CurrentURL .IPListsURL}} active{{- end}}" href="{{.IPListsURL}}">
|
||||||
<span class="menu-bullet">
|
<span class="menu-bullet">
|
||||||
|
@ -191,7 +191,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{- end}}
|
{{- end}}
|
||||||
{{- if or (.LoggedUser.HasPermission "manage_system") (.LoggedUser.HasPermission "view_status") (and .HasSearcher (.LoggedUser.HasPermission "view_events"))}}
|
{{- if or (.LoggedUser.HasPermission "*") (.LoggedUser.HasPermission "view_status") (and .HasSearcher (.LoggedUser.HasPermission "view_events"))}}
|
||||||
<div data-kt-menu-trigger="click" class="menu-item menu-accordion {{- if .IsServerManagerPage}} here show{{- end}}">
|
<div data-kt-menu-trigger="click" class="menu-item menu-accordion {{- if .IsServerManagerPage}} here show{{- end}}">
|
||||||
<span class="menu-link">
|
<span class="menu-link">
|
||||||
<span class="menu-icon">
|
<span class="menu-icon">
|
||||||
|
@ -207,7 +207,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
<span class="menu-arrow"></span>
|
<span class="menu-arrow"></span>
|
||||||
</span>
|
</span>
|
||||||
<div class="menu-sub menu-sub-accordion">
|
<div class="menu-sub menu-sub-accordion">
|
||||||
{{- if .LoggedUser.HasPermission "manage_system"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<div class="menu-item">
|
<div class="menu-item">
|
||||||
<a class="menu-link {{- if eq .CurrentURL .ConfigsURL}} active{{- end}}" href="{{.ConfigsURL}}">
|
<a class="menu-link {{- if eq .CurrentURL .ConfigsURL}} active{{- end}}" href="{{.ConfigsURL}}">
|
||||||
<span class="menu-bullet">
|
<span class="menu-bullet">
|
||||||
|
@ -227,7 +227,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
{{- end}}
|
{{- end}}
|
||||||
{{- if .LoggedUser.HasPermission "manage_system"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<div class="menu-item">
|
<div class="menu-item">
|
||||||
<a class="menu-link {{- if eq .CurrentURL .MaintenanceURL}} active{{- end}}" href="{{.MaintenanceURL}}">
|
<a class="menu-link {{- if eq .CurrentURL .MaintenanceURL}} active{{- end}}" href="{{.MaintenanceURL}}">
|
||||||
<span class="menu-bullet">
|
<span class="menu-bullet">
|
||||||
|
@ -250,7 +250,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{- end}}
|
{{- end}}
|
||||||
{{- if .LoggedUser.HasPermission "manage_admins"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<div class="menu-item">
|
<div class="menu-item">
|
||||||
<a class="menu-link {{- if eq .CurrentURL .AdminsURL}} active{{- end}}" href="{{.AdminsURL}}">
|
<a class="menu-link {{- if eq .CurrentURL .AdminsURL}} active{{- end}}" href="{{.AdminsURL}}">
|
||||||
<span class="menu-icon">
|
<span class="menu-icon">
|
||||||
|
@ -259,8 +259,6 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
<span data-i18n="title.admins" class="menu-title">Admins</span>
|
<span data-i18n="title.admins" class="menu-title">Admins</span>
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
{{- end}}
|
|
||||||
{{- if .LoggedUser.HasPermission "manage_roles"}}
|
|
||||||
<div class="menu-item">
|
<div class="menu-item">
|
||||||
<a class="menu-link {{- if eq .CurrentURL .RolesURL}} active{{- end}}" href="{{.RolesURL}}">
|
<a class="menu-link {{- if eq .CurrentURL .RolesURL}} active{{- end}}" href="{{.RolesURL}}">
|
||||||
<span class="menu-icon">
|
<span class="menu-icon">
|
||||||
|
|
|
@ -38,7 +38,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
class="form-control rounded-1 w-250px ps-15 me-5" placeholder="Search" />
|
class="form-control rounded-1 w-250px ps-15 me-5" placeholder="Search" />
|
||||||
</div>
|
</div>
|
||||||
<div class="d-flex justify-content-end my-2" data-table-toolbar="base">
|
<div class="d-flex justify-content-end my-2" data-table-toolbar="base">
|
||||||
{{- if .LoggedUser.HasPermission "manage_event_rules"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<a href="{{.EventActionURL}}" class="btn btn-primary ms-5">
|
<a href="{{.EventActionURL}}" class="btn btn-primary ms-5">
|
||||||
<i class="ki-duotone ki-plus fs-2"></i>
|
<i class="ki-duotone ki-plus fs-2"></i>
|
||||||
<span data-i18n="general.add">Add</span>
|
<span data-i18n="general.add">Add</span>
|
||||||
|
@ -231,7 +231,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</button>
|
</button>
|
||||||
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
||||||
|
|
||||||
//{{- if .LoggedUser.HasPermission "manage_event_rules"}}
|
//{{- if .LoggedUser.HasPermission "*"}}
|
||||||
numActions++;
|
numActions++;
|
||||||
actions+=`<div class="menu-item px-3">
|
actions+=`<div class="menu-item px-3">
|
||||||
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
||||||
|
|
|
@ -38,7 +38,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
class="form-control rounded-1 w-250px ps-15 me-5" placeholder="Search" />
|
class="form-control rounded-1 w-250px ps-15 me-5" placeholder="Search" />
|
||||||
</div>
|
</div>
|
||||||
<div class="d-flex justify-content-end my-2" data-table-toolbar="base">
|
<div class="d-flex justify-content-end my-2" data-table-toolbar="base">
|
||||||
{{- if .LoggedUser.HasPermission "manage_event_rules"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<a href="{{.EventRuleURL}}" class="btn btn-primary ms-5">
|
<a href="{{.EventRuleURL}}" class="btn btn-primary ms-5">
|
||||||
<i class="ki-duotone ki-plus fs-2"></i>
|
<i class="ki-duotone ki-plus fs-2"></i>
|
||||||
<span data-i18n="general.add">Add</span>
|
<span data-i18n="general.add">Add</span>
|
||||||
|
@ -283,7 +283,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</button>
|
</button>
|
||||||
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
||||||
|
|
||||||
//{{- if .LoggedUser.HasPermission "manage_event_rules"}}
|
//{{- if .LoggedUser.HasPermission "*"}}
|
||||||
numActions++;
|
numActions++;
|
||||||
actions+=`<div class="menu-item px-3">
|
actions+=`<div class="menu-item px-3">
|
||||||
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
||||||
|
|
|
@ -290,7 +290,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
||||||
</div>`;
|
</div>`;
|
||||||
//{{- end}}
|
//{{- end}}
|
||||||
//{{- if .LoggedUser.HasPermission "manage_system"}}
|
//{{- if .LoggedUser.HasPermission "*"}}
|
||||||
numActions++;
|
numActions++;
|
||||||
actions+=`<div class="menu-item px-3">
|
actions+=`<div class="menu-item px-3">
|
||||||
<a data-i18n="general.template" href="#" class="menu-link px-3" data-table-action="template_row">Template</a>
|
<a data-i18n="general.template" href="#" class="menu-link px-3" data-table-action="template_row">Template</a>
|
||||||
|
|
|
@ -57,7 +57,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</label>
|
</label>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{{- if .LoggedUser.HasPermission "manage_roles"}}
|
{{- if .LoggedUser.HasPermission "*"}}
|
||||||
<a href="{{.RoleURL}}" class="btn btn-primary ms-5">
|
<a href="{{.RoleURL}}" class="btn btn-primary ms-5">
|
||||||
<i class="ki-duotone ki-plus fs-2"></i>
|
<i class="ki-duotone ki-plus fs-2"></i>
|
||||||
<span data-i18n="general.add">Add</span>
|
<span data-i18n="general.add">Add</span>
|
||||||
|
@ -226,7 +226,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
</button>
|
</button>
|
||||||
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
<div class="menu menu-sub menu-sub-dropdown menu-column menu-rounded menu-gray-700 menu-state-bg-light-primary fw-semibold fs-6 w-200px py-4" data-kt-menu="true">`;
|
||||||
|
|
||||||
//{{- if .LoggedUser.HasPermission "manage_roles"}}
|
//{{- if .LoggedUser.HasPermission "*"}}
|
||||||
numActions++;
|
numActions++;
|
||||||
actions+=`<div class="menu-item px-3">
|
actions+=`<div class="menu-item px-3">
|
||||||
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
||||||
|
|
|
@ -533,7 +533,7 @@ explicit grant from the SFTPGo Team (support@sftpgo.com).
|
||||||
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
<a data-i18n="general.edit" href="#" class="menu-link px-3" data-table-action="edit_row">Edit</a>
|
||||||
</div>`;
|
</div>`;
|
||||||
//{{- end}}
|
//{{- end}}
|
||||||
//{{- if .LoggedUser.HasPermission "manage_system"}}
|
//{{- if .LoggedUser.HasPermission "*"}}
|
||||||
numActions++;
|
numActions++;
|
||||||
actions+=`<div class="menu-item px-3">
|
actions+=`<div class="menu-item px-3">
|
||||||
<a data-i18n="general.template" href="#" class="menu-link px-3" data-table-action="template_row">Template</a>
|
<a data-i18n="general.template" href="#" class="menu-link px-3" data-table-action="template_row">Template</a>
|
||||||
|
|
Loading…
Reference in a new issue