… or how to turn every e-mail notification in a custom alert in Microsoft Sentinel and customize alert details for your benefit.
Microsoft Defender for Identity offers no API integration for health information, but those information are crucial. If one or more sensors in your environment have problems capturing data, you might miss out on important telemetry and attacks could go undetected.
What MDI offers are e-mail notifications. But monitoring a mailbox is not really great and offers no integration in the incident management capabilities of Microsoft Sentinel. So our goal for today, is to create an incident in Sentinel every time a MDI health issue occurs.
Prerequisites
If you want to implement the solution I outline in this article you will need to have a few things in place
Microsoft Defender for Identity
Microsoft Defender for Office 365
Microsoft Sentinel
Sentinel data connectors:
Microsoft 365 Defender (Alerts & Incidents)
Microsoft 365 Defender (EmailEvents table)
Notiz
You can also achieve a similar solution without Sentinel using custom detections in MDE, but you will miss out on some of the additional customization I will use in Sentinel.
E-Mail alerts
You can configure one or multiple e-mail addresses, that should be contacted in the case of an health issue with one of the MDI sensors. Add at least one mailbox within you tenant to that list. This mailbox does not have to be monitored.
Health issue notification configuration
Should any of the sensor fail or encounter a different health alert, you will receive an email.
E-Mail send when health issue occurs
EmailEvents table
With this setup in place the EmailEvents table comes into play. First you will need to forward those events to Sentinel.
Data connector
Make sure that the “Microsoft 365 Defender (Preview)” data connector in Sentinel is enabled.
Enable the Microsoft 365 Defender connector
To get information about incoming emails you will need to forward the EmailEvents table to Sentinel as well.
Forward the table EmailEvents in the Defender for Office 365 category of the data connector
Info
This will add additional ingestion cost to Microsoft Sentinel .
Query
The easiest query you can use to identify any incoming e-mail alerts from MDI is the following. It just returns a list of all received email from the Defender e-mail address.
Sadly, the affected CI is not part of the subject, therefore we cannot add the name of the domain controller as well.
But there is still more we can do to help us when working with the the incident.
EmailEvents|whereSenderFromAddress=="defender-noreply@microsoft.com"|extendMDIWorkspace=extract(@"(^.*) Workspace",1,Subject)|extendSeverity=extract(@" \[(.*)\] ",1,Subject)|extendAlertTitle=extract(@"\] (.*)$",1,Subject)|summarizebybin(TimeGenerated,10m),MDIWorkspace,Severity,AlertTitle|extendProductName="Microsoft Defender for Identity"|extendAlertLink="https://security.microsoft.com/settings/identities?tabid=healthIssues"
As you can see here I added a summarize by bin(TimeGenerated, 10min) and also a column for ProductName and AlertLink.
The summarize operator is used to remove any duplicated alerts with a 10 minutes time windows. Should you have configured more than one e-mail recipient, this will consolidate those emails into one event.
The product name and alert link information is static and will be later shown as part of the incident.
Analytics Rule
With all this data, let’s build an analytics rule using this query. Create a new scheduled rule and enter a good title as well as an description.
Create a new Analytics Rule...
Next, paste the query provided.
EmailEvents|whereSenderFromAddress=="defender-noreply@microsoft.com"|extendMDIWorkspace=extract(@"(^.*) Workspace",1,Subject)|extendSeverity=extract(@" \[(.*)\] ",1,Subject)|extendAlertTitle=extract(@"\] (.*)$",1,Subject)|summarizebybin(TimeGenerated,10m),MDIWorkspace,Severity,AlertTitle|extendProductName="Microsoft Defender for Identity"|extendAlertLink="https://security.microsoft.com/settings/identities?tabid=healthIssues"
...paste the kusto query...
The additional information provided and extracted from the subject line will be used to customize the alert details and further enhance the enrichment of the incident. As you can see we can not only create an dynamic alert title, but also customize the description, severity, the alert link and the product name using the fields we created.
...configure the alert details...
I will let run this analytics rule every 20 minutes, with the same lookup time interval and create an incident as soon as an incoming email is found. Also I prevent the events from being grouped to make sure every seperate alert creates a seperate incident.
...configure the query scheduling interval and save the analytics rule.
All other settings in the wizard can be left alone and the Analytics rule can be saved as configured.
At the end of this blog post you will also find the corresponding YAML and ARM template, if you don’t like to click so much or copy over the exact values.
Incident
The next time you encounter an MDI health error this analytics rule will create an incident for you.
As you can see the additional steps to customize the incident can help immensely to identify the issue at hand, without leaving the Sentinel incident view.
Sample incidents
Besides the custom incident title the description is dynamically based on the values received via email.
And as a bonus even the alert product name is populated and there is even a “Investigate externally” link at the top, that directly takes you to the MDI health portal website.
Incident enriched with custom information
Conclusion
Using the different data sources provided in Microsoft Sentinel gives you not only great threat hunting capabilities, you can also use this information to alert on potential blind spots in your environment. Together with Microsoft Defender for Office 365 and native e-mail alerting capabilities of any product you can add additional value directly into the consolidated incidents view of Microsoft Sentinel .
Template deployment
Of course it’s much easier to use a YAML file or ARM file to deploy those settings. So here you go.
id:b90dfa8b-0ea3-4c6d-8e7c-0ec102e9854cname:'[Monitoring] MDI sensor health issue'description:One of the Microsoft Defender for Identity sensors has an health issue, which must be resolved for full coverage of MDI in your environment.severity:Informationalenabled:truequery:|- EmailEvents
| where SenderFromAddress == "defender-noreply@microsoft.com"
| extend MDIWorkspace = extract(@"(^.*) Workspace", 1, Subject)
| extend Severity = extract(@" \[(.*)\] ", 1, Subject)
| extend AlertTitle = extract(@"\] (.*)$", 1, Subject)
| summarize by bin(TimeGenerated, 10m), MDIWorkspace, Severity, AlertTitle
| extend ProductName = "Microsoft Defender for Identity"
| extend AlertLink = "https://security.microsoft.com/settings/identities?tabid=healthIssues"queryFrequency:20mqueryPeriod:20mtriggerOperator:GreaterThantriggerThreshold:0suppressionDuration:5hsuppressionEnabled:falsetactics:[]relevantTechniques:[]incidentConfiguration:createIncident:truegroupingConfiguration:enabled:falsereopenClosedIncident:falselookbackDuration:5hmatchingMethod:AllEntitiesgroupByEntities:[]groupByAlertDetails:[]groupByCustomDetails:[]eventGroupingSettings:aggregationKind:AlertPerResultalertDetailsOverride:alertnameFormat:'[Monitoring] [MDI] {{AlertTitle}}'alertDescriptionFormat:|- One of the Microsoft Defender for Identity sensors in workspace {{MDIWorkspace}} has the following health issue:
{{AlertTitle}}
Please check the health issues site on the M365 Defender portalalertSeverityColumnName:SeverityalertDynamicProperties:- alertProperty:ProductNamevalue:ProductName- alertProperty:AlertLinkvalue:AlertLink
{"$schema":"https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#","contentVersion":"1.0.0.0","parameters":{"workspace":{"type":"String"}},"resources":[{"id":"[concat(resourceId('Microsoft.OperationalInsights/workspaces/providers', parameters('workspace'), 'Microsoft.SecurityInsights'),'/alertRules/b90dfa8b-0ea3-4c6d-8e7c-0ec102e9854c')]","name":"[concat(parameters('workspace'),'/Microsoft.SecurityInsights/b90dfa8b-0ea3-4c6d-8e7c-0ec102e9854c')]","type":"Microsoft.OperationalInsights/workspaces/providers/alertRules","kind":"Scheduled","apiVersion":"2022-10-01-preview","properties":{"alertRuleTemplateName":"b90dfa8b-0ea3-4c6d-8e7c-0ec102e9854c","displayName":"[Monitoring] MDI sensor health issue","techniques":[],"description":"One of the Microsoft Defender for Identity sensors has an health issue, which must be resolved for full coverage of MDI in your environment.","severity":"Informational","enabled":true,"query":"EmailEvents\n| where SenderFromAddress == \"defender-noreply@microsoft.com\"\n| extend MDIWorkspace = extract(@\"(^.*) Workspace\", 1, Subject)\n| extend Severity = extract(@\" \\[(.*)\\] \", 1, Subject)\n| extend AlertTitle = extract(@\"\\] (.*)$\", 1, Subject)\n| summarize by bin(TimeGenerated, 10m), MDIWorkspace, Severity, AlertTitle\n| extend ProductName = \"Microsoft Defender for Identity\"\n| extend AlertLink = \"https://security.microsoft.com/settings/identities?tabid=healthIssues\"","queryFrequency":"PT20M","queryPeriod":"PT20M","triggerOperator":"GreaterThan","triggerThreshold":0,"suppressionDuration":"PT5H","suppressionEnabled":false,"tactics":[],"incidentConfiguration":{"groupingConfiguration":{"enabled":false,"reopenClosedIncident":false,"matchingMethod":"AllEntities","groupByEntities":[],"lookbackDuration":"PT5H","groupByAlertDetails":[],"groupByCustomDetails":[]},"createIncident":true},"eventGroupingSettings":{"aggregationKind":"AlertPerResult"},"alertDetailsOverride":{"alertnameFormat":"[Monitoring] [MDI] {{AlertTitle}}","alertSeverityColumnName":"Severity","alertDynamicProperties":[{"alertProperty":"ProductName","value":"ProductName"},{"alertProperty":"AlertLink","value":"AlertLink"}],"alertDescriptionFormat":"One of the Microsoft Defender for Identity sensors in workspace {{MDIWorkspace}} has the following health issue:\n\n{{AlertTitle}}\n\nPlease check the health issues site on the M365 Defender portal"},"customDetails":null,"entityMappings":null,"sentinelEntitiesMappings":null}}]}