Detection rules › Sigma
High risk event - grant Management APIs scopes
Excessive permissions can lead to unauthorized access. Auth0 Management API scopes should be given to trusted applications and monitored.
MITRE ATT&CK coverage
| Tactic | Techniques |
|---|---|
| Privilege Escalation | T1548 Abuse Elevation Control Mechanism |
Rule body yaml
title: High risk event - grant Management APIs scopes
id: b275f0fa-3f2d-493f-a741-67e861ef77ed
status: experimental
description: |
Excessive permissions can lead to unauthorized access. Auth0 Management API scopes should be given to trusted applications and monitored.
author: Okta
date: 2025-07-11
modified: 2025-09-01
logsource:
product: auth0
detection:
selection:
data.type: sapi
data.description:
- Update client grant
filter_1:
data.details.response.body.audience:
- 'https://{your-tenant-domain}/api/v2/'
data.details.request.body.scope{}|startswith:
# Example of scopes. Limit this list to relevant scopes to be monitored
- 'delete:'
- 'update:'
filter_2:
data.details.response.body.client_id:
# List client_ids for trusted applications
- '{trusted-client_id-1}'
- '{trusted-client_id-2}'
condition: selection and filter_1 and not filter_2
explanation: >
The query collects log entries issued when applications' settings are modified, i.e. "Update client grant".
It filters by audience to locate Management API related activities.
The Splunk query provides modifying IPs, client_ids of applications which were assigned to risky scopes, and a list of these scopes.
splunk: |
index=auth0 data.tenant_name="{your-tenant-name}"
data.type=sapi data.description="Update client grant"
data.details.response.body.audience="https://{your-tenant-domain}/api/v2/"
```Add more monitored scopes```
data.details.request.body.scope{} IN ("{mgg-api-scope-1}", "{mgg-api-scope-2}")
```Trigger an alert when scopes are granted to applications that are not on the list of allowed clients.```
NOT data.details.response.body.client_id IN ({trusted-client_id-1}, {trusted-client_id-2})
| fields _time, data.ip, data.details.request.body.scope{}, data.details.response.body.client_id
```Display the information in a table```
| table _time, data.ip, data.details.response.body.client_id, data.details.request.body.scope{}
comments:
- The Splunk query above shall be tuned to reflect a valid tenant name, audience, monitored Management API scopes, and trusted client_ids.
- To reduce a number of alerts, the query can be adjusted to watch for a more critical set of scopes, e.g. focus on "delete:*", but not "read:*",
and/or trigger alerts when scopes are granted to applications that are not on the list of trusted clients.
- To get a full list of available Management APIs scope and their descriptions, you can go to Applications --> Auth0 Management API --> Permissions.
- To get an easier to copy list, you can go to Applications --> Auth0 Management API --> API Explorer --> Copy the token.
- Then go to Management API documentation (https://auth0.com/docs/api/management/v2), click "Set API Token" and paste the earlier copied token. Now, you see all scopes that are easy to copy and use in the splunk query given above.
tenant_logs: |
type:"sapi" AND description: "Update client grant"
prevention:
- Control tenant admins, i.e. "Admin", as this role has permissions to modify any application.
- Enforce MFA for tenant admins to reduce the risk of an adversary gaining access.
- Control Management API scopes that allow modification of grants - *:client_grants
- Control usage of Management API from only trusted IPs by applying Network ACL scoped to "management".
falsepositives:
- Legitimate updates by an administrator. This rule is designed for threat hunting and to be a starting point for further investigation.
- Trusted client_id has not been listed, e.g. see filter_2.
level: medium
tags:
- attack.defense-evasion
- attack.t1548
Stages and Predicates
Stage 0: condition
selection and filter_1 and not filter_2Stage 1: selection
selection:
data.type: sapi
data.description:
- Update client grant
Stage 2: filter_1
filter_1:
data.details.response.body.audience:
- 'https://{your-tenant-domain}/api/v2/'
data.details.request.body.scope{}|startswith:
- 'delete:'
- 'update:'
Stage 3: not filter_2
filter_2:
data.details.response.body.client_id:
- '{trusted-client_id-1}'
- '{trusted-client_id-2}'
Exclusions
Top-level NOT(...) conjuncts: predicates this rule actively suppresses.
| Field | Kind | Excluded values |
|---|---|---|
data.details.response.body.client_id | eq | {trusted-client_id-1} |
data.details.response.body.client_id | eq | {trusted-client_id-2} |
Indicators
Each row is a field, operator, and value that the rule matches. The corpus column counts how many other rules in the catalog look for the same combination: high numbers point to widely-used, community-vetted indicators. Blank or 1 shows that the indicator is specific to this rule.
| Field | Kind | Values |
|---|---|---|
data.description | eq |
|
data.details.request.body.scope{} | starts_with |
|
data.details.response.body.audience | eq |
|
data.type | eq |
|