Sensitive Keyword Search via Graph
Platform
Data Sources
Related Blog Post
Read the full blog post about this hunt →MITRE ATT&CK
Tactics
Techniques
Threat Actors
Tags
Hunt Hypothesis
Threat Actors will use token theft as a means of initial access, privilege escalation and persistence. Poorly secured tokens by third parties can increase the risk of token theft and replay.
Sensitive Keyword Search via Graph
Analytic #1This looks for sensitive key words being searched across mail, files and sharepoint via the GraphAPI. Utilises Graph API activity logs.
Detection Queries
let SensitiveKeywords = dynamic(["password", "secret", "confidential", "credentials", "api key", "apikey", "token", "private", "sensitive", "internal", "restricted", "ssn", "social security", "credit card"]);
let GraphSearches =
MicrosoftGraphActivityLogs
| where RequestUri contains "/messages" and RequestUri contains "%24search"
or RequestUri contains "/drive/root/search"
or RequestUri contains "/drive/" and RequestUri contains "search"
or RequestUri contains "/sites" and RequestUri contains "search"
or RequestUri contains "/search/query"
| extend DecodedUri = url_decode(RequestUri)
| where DecodedUri has_any (SensitiveKeywords)
| extend SearchTerm = case(
RequestUri contains "%24search", extract(@'%24search=([^&]*)', 1, RequestUri),
RequestUri contains "/search(q=", extract(@'/search\(q=''([^'']*)', 1, RequestUri),
RequestUri contains "/search?q=", extract(@'/search\?q=([^&]*)', 1, RequestUri),
"")
| extend DecodedSearchTerm = url_decode(SearchTerm)
| extend ResourceType = case(
RequestUri contains "/messages", "Email",
RequestUri contains "/drive", "OneDrive/SharePoint Files",
RequestUri contains "/sites", "SharePoint Sites",
"Other");
let AADLogs =
AADNonInteractiveUserSignInLogs
| project AppId, UserId, Identity, AppDisplayName, AADLocation = Location;
GraphSearches
| join kind=leftouter (AADLogs) on AppId, UserId
| project TimeGenerated, SignInActivityId, Identity, AppDisplayName, IPAddress, UserAgent,
ResourceType, RequestMethod, DecodedUri, DecodedSearchTerm, ResponseStatusCode,
Location, AADLocation
| order by TimeGenerated desc
Triage Steps
- Review the specific sensitive keywords being searched for in the alert
- Identify which resource type was targeted (Email, OneDrive, SharePoint)
- Check if the user has a legitimate business reason to search for sensitive terms
- Investigate the application making the requests and verify it's authorized
- Review the UserAgent to identify if automated tooling is being used
- Check the response codes to see if the searches were successful
- Look for patterns of multiple sensitive keyword searches in a short timeframe
- If malicious, investigate what data may have been accessed and consider revoking app access
True Positive Example
Example 1
{
"TimeGenerated": "06/12/2025, 14:13:48.444",
"SignInActivityId": "70ObFHiCDUW42aMM2OEcAA",
"Identity": "Hunter",
"AppDisplayName": "TruffleHog Test App",
"IPAddress": "79.135.105.18",
"UserAgent": "data_exfil_tool",
"ResourceType": "Email",
"RequestMethod": "GET",
"DecodedUri": "https://graph.microsoft.com/v1.0/me/messages?$search=\"secret\"&$select=subject,from,receivedDateTime,hasAttachments,bodyPreview&$top=5",
"DecodedSearchTerm": "\"secret\"",
"ResponseStatusCode": "200",
"Location": "UAE North",
"AADLocation": "AZ"
} Attacker searching user emails for the keyword 'secret' via Graph API. The custom UserAgent 'data_exfil_tool' and successful 200 response indicates automated credential harvesting activity.
Example 2
{
"TimeGenerated": "06/12/2025, 14:13:48.444",
"SignInActivityId": "70ObFHiCDUW42aMM2OEcAA",
"Identity": "Hunter",
"AppDisplayName": "TruffleHog Test App",
"IPAddress": "79.135.105.18",
"UserAgent": "data_exfil_tool",
"ResourceType": "Email",
"RequestMethod": "GET",
"DecodedUri": "https://graph.microsoft.com/v1.0/me/messages?$search=\"secret\"&$select=subject,from,receivedDateTime,hasAttachments,bodyPreview&$top=5",
"DecodedSearchTerm": "\"secret\"",
"ResponseStatusCode": "200",
"Location": "UAE North",
"AADLocation": "AZ"
} Multiple searches for sensitive keywords across email indicates systematic data reconnaissance. The attacker is likely building a profile of sensitive information accessible via the compromised token.
Example 3
{
"TimeGenerated": "06/12/2025, 13:43:51.184",
"SignInActivityId": "70ObFHiCDUW42aMM2OEcAA",
"Identity": "Hunter",
"AppDisplayName": "TruffleHog Test App",
"IPAddress": "79.135.105.18",
"UserAgent": "data_exfil_tool",
"ResourceType": "Email",
"RequestMethod": "GET",
"DecodedUri": "https://graph.microsoft.com/v1.0/me/messages?$search=\"confidential\"&$select=subject,from,receivedDateTime,hasAttachments,bodyPreview&$top=5",
"DecodedSearchTerm": "\"confidential\"",
"ResponseStatusCode": "200",
"Location": "Poland Central",
"AADLocation": "AZ"
} Continuation of keyword-based email searches, now targeting 'confidential' content. The pattern of searching for various sensitive terms suggests an organized data exfiltration campaign.