Alerting: Update provisioning API to support regular permissions (#77007)
* allow users with regular actions access provisioning API paths * update methods that read rules skip new authorization logic if user CanReadAllRules to avoid performance impact on file-provisioning update all methods to accept identity.Requester that contains all permissions and is required by access control. * create deltas for single rul e * update modify methods skip new authorization logic if user CanWriteAllRules to avoid performance impact on file-provisioning update all methods to accept identity.Requester that contains all permissions and is required by access control. * implement RuleAccessControlService in provisioning * update file provisioning user to have all permissions to bypass authz * update provisioning API to return errutil errors correctly --------- Co-authored-by: Alexander Weaver <weaver.alex.d@gmail.com>
This commit is contained in:
co-authored by
Alexander Weaver
parent
0b4830ccfd
commit
b9abb8cabb
@@ -223,19 +223,90 @@ func (api *API) authorize(method, path string) web.Handler {
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningReadSecrets), // organization scope
|
||||
)
|
||||
|
||||
case http.MethodGet + "/api/v1/provisioning/alert-rules",
|
||||
http.MethodGet + "/api/v1/provisioning/alert-rules/export":
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningRead),
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningReadSecrets),
|
||||
ac.EvalAll( // scopes are enforced in the handler
|
||||
ac.EvalPermission(ac.ActionAlertingRuleRead),
|
||||
ac.EvalPermission(dashboards.ActionFoldersRead),
|
||||
),
|
||||
)
|
||||
case http.MethodGet + "/api/v1/provisioning/alert-rules/{UID}",
|
||||
http.MethodGet + "/api/v1/provisioning/alert-rules/{UID}/export":
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningRead),
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningReadSecrets),
|
||||
ac.EvalAll(
|
||||
ac.EvalPermission(ac.ActionAlertingRuleRead),
|
||||
ac.EvalPermission(dashboards.ActionFoldersRead),
|
||||
),
|
||||
)
|
||||
|
||||
case http.MethodGet + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}",
|
||||
http.MethodGet + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}/export":
|
||||
scope := dashboards.ScopeFoldersProvider.GetResourceScopeUID(ac.Parameter(":FolderUID"))
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningRead),
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningReadSecrets),
|
||||
ac.EvalAll(
|
||||
ac.EvalPermission(ac.ActionAlertingRuleRead, scope),
|
||||
ac.EvalPermission(dashboards.ActionFoldersRead, scope),
|
||||
),
|
||||
)
|
||||
|
||||
case http.MethodGet + "/api/v1/provisioning/policies",
|
||||
http.MethodGet + "/api/v1/provisioning/contact-points",
|
||||
http.MethodGet + "/api/v1/provisioning/templates",
|
||||
http.MethodGet + "/api/v1/provisioning/templates/{name}",
|
||||
http.MethodGet + "/api/v1/provisioning/mute-timings",
|
||||
http.MethodGet + "/api/v1/provisioning/mute-timings/{name}",
|
||||
http.MethodGet + "/api/v1/provisioning/alert-rules",
|
||||
http.MethodGet + "/api/v1/provisioning/alert-rules/{UID}",
|
||||
http.MethodGet + "/api/v1/provisioning/alert-rules/export",
|
||||
http.MethodGet + "/api/v1/provisioning/alert-rules/{UID}/export",
|
||||
http.MethodGet + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}",
|
||||
http.MethodGet + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}/export":
|
||||
eval = ac.EvalAny(ac.EvalPermission(ac.ActionAlertingProvisioningRead), ac.EvalPermission(ac.ActionAlertingProvisioningReadSecrets)) // organization scope
|
||||
http.MethodGet + "/api/v1/provisioning/mute-timings/{name}":
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningRead),
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningReadSecrets),
|
||||
)
|
||||
|
||||
// Grafana-only Provisioning Write Paths
|
||||
case http.MethodPost + "/api/v1/provisioning/alert-rules":
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningWrite),
|
||||
ac.EvalPermission(ac.ActionAlertingRuleCreate), // more granular permissions are enforced by the handler via "authorizeRuleChanges"
|
||||
)
|
||||
case http.MethodPut + "/api/v1/provisioning/alert-rules/{UID}":
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningWrite),
|
||||
ac.EvalPermission(ac.ActionAlertingRuleUpdate), // more granular permissions are enforced by the handler via "authorizeRuleChanges"
|
||||
)
|
||||
case http.MethodDelete + "/api/v1/provisioning/alert-rules/{UID}":
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningWrite),
|
||||
ac.EvalPermission(ac.ActionAlertingRuleDelete), // more granular permissions are enforced by the handler via "authorizeRuleChanges"
|
||||
)
|
||||
case http.MethodDelete + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}":
|
||||
scope := dashboards.ScopeFoldersProvider.GetResourceScopeUID(ac.Parameter(":FolderUID"))
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningWrite),
|
||||
ac.EvalAll(
|
||||
ac.EvalPermission(ac.ActionAlertingRuleDelete, scope),
|
||||
ac.EvalPermission(ac.ActionAlertingRuleRead, scope),
|
||||
ac.EvalPermission(dashboards.ActionFoldersRead, scope),
|
||||
),
|
||||
)
|
||||
case http.MethodPut + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}":
|
||||
scope := dashboards.ScopeFoldersProvider.GetResourceScopeUID(ac.Parameter(":FolderUID"))
|
||||
eval = ac.EvalAny(
|
||||
ac.EvalPermission(ac.ActionAlertingProvisioningWrite),
|
||||
ac.EvalAll(
|
||||
ac.EvalPermission(ac.ActionAlertingRuleRead, scope),
|
||||
ac.EvalPermission(dashboards.ActionFoldersRead, scope),
|
||||
ac.EvalAny( // the exact permissions will be checked after the operations are determined
|
||||
ac.EvalPermission(ac.ActionAlertingRuleUpdate, scope),
|
||||
ac.EvalPermission(ac.ActionAlertingRuleCreate, scope),
|
||||
ac.EvalPermission(ac.ActionAlertingRuleDelete, scope),
|
||||
),
|
||||
),
|
||||
)
|
||||
|
||||
case http.MethodPut + "/api/v1/provisioning/policies",
|
||||
http.MethodDelete + "/api/v1/provisioning/policies",
|
||||
@@ -246,12 +317,7 @@ func (api *API) authorize(method, path string) web.Handler {
|
||||
http.MethodDelete + "/api/v1/provisioning/templates/{name}",
|
||||
http.MethodPost + "/api/v1/provisioning/mute-timings",
|
||||
http.MethodPut + "/api/v1/provisioning/mute-timings/{name}",
|
||||
http.MethodDelete + "/api/v1/provisioning/mute-timings/{name}",
|
||||
http.MethodPost + "/api/v1/provisioning/alert-rules",
|
||||
http.MethodPut + "/api/v1/provisioning/alert-rules/{UID}",
|
||||
http.MethodDelete + "/api/v1/provisioning/alert-rules/{UID}",
|
||||
http.MethodPut + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}",
|
||||
http.MethodDelete + "/api/v1/provisioning/folder/{FolderUID}/rule-groups/{Group}":
|
||||
http.MethodDelete + "/api/v1/provisioning/mute-timings/{name}":
|
||||
eval = ac.EvalPermission(ac.ActionAlertingProvisioningWrite) // organization scope
|
||||
case http.MethodGet + "/api/v1/notifications/time-intervals/{name}",
|
||||
http.MethodGet + "/api/v1/notifications/time-intervals":
|
||||
|
||||
Reference in New Issue
Block a user