How to Use Azure Logic Apps to Create a More Detailed Azure Monitor Alert
A common scenario we experienced when working with partners is the need to create more details alerts in Azure. Currently, the default alert you configure when you set up Azure Monitor Alert looks like this:
As a partner that likely must manage multiple customer environments, these default alerts don’t provide enough information to be able to quickly identify which tenant is the one that is impacted. Some information that could be included in the alert that can help with this include:
Customer impacted.
Subscription of the customer impacted.
Resources impacted.
Fortunately, there are several workarounds for this. The goal is to turn the above alert into this:
In this blog post, we will delve into the process of crafting comprehensive alerts using Azure Logic App. Our discussion will encompass the following key points:
Establishing the foundation of Azure Logic App
Enhancing the depth of information within your alerts
Exploring noteworthy Azure Logic App Connectors
A step-by-step guide through the logic app configuration
It's important to acknowledge that one of the remarkable aspects of Azure Logic Apps is the versatility it offers. There exist multiple pathways to achieve similar outcomes. Hence, this blog serves not only as a guide but also as an avenue for inspiration.
We encourage all readers to consider methods for refining the presented concepts and contemplate how these insights can seamlessly integrate with various other scenarios. Your innovative approach can elevate the capabilities of Azure Logic Apps even further.
How to setup Azure Logic Apps
There are two main models for setting up Azure Logic Apps these are:
Model 1 - Azure Monitor alert and Logic App components are stored on the customer tenant.
Model 2 - Azure Monitor alert runs on the customer tenant, and the Azure Logic App Component runs on the partner side.
Model 1 - Azure Monitor alert and Logic App components are stored on the customer tenant
In this example, the partner manages two customers over Azure Lighthouse; the Azure monitor alerts and playbooks are stored and run on the tenant’s tenant.
Considerations for this model:
Logic App execution price is charged to the customer.
The customer is responsible for the charges associated with Azure Monitor Alerts.
Monitoring for both success and failure necessitates observation within the customer's environment.
Model 2 - Azure Monitor alert runs on the customer tenant, and the Azure Logic App Component runs on the partner side
In this example, the partner manages two customers over Azure Lighthouse; the Azure monitor alerts are stored and managed in the customer’s tenant. The Azure Logic App is stored in the partner tenant. A secure webhook or the Azure Logic App action type will be used to trigger the Azure Logic App. Note that although it’s possible to use a non-secure webhook. We don’t recommend this, as no built-in authentication or encryption exists.
Considerations for this model:
Logic App execution price is charged to the partner.
Azure Monitor alert price is charged to the customer.
An action group that triggers a Webhook or Azure Logic App.
The Common Alert Schema standardizes the consumption of Azure Monitor alert notifications. Historically, activity log, metric, and log alerts had their own email templates and Webhook schemas. The Common Alert Schema provides one standardized schema for all alert notifications.
Using a standardized schema helps minimize the number of integrations, simplifying managing and maintaining your integrations. The common schema enables a richer alert consumption experience in the Azure portal and the Azure mobile app.
The Common Alert Schema will also provide access to more information and the means to obtain more information using other logic app connectors.
The Common Alert Schema provides a consistent structure for:
Email templates: Use the detailed email template to diagnose issues at a glance. Embedded links to the alert instance on the portal and the affected resource ensure you can quickly jump into the remediation process.
JSON structure: Use the consistent JSON structure to build integrations for all alert types using:
Azure Logic Apps
Azure Functions
Azure Automation runbook
Here is an example of the contents you get from the Common Alert Schema:
{
"schemaId": "azureMonitorCommonAlertSchema",
"data": {
"essentials": {
"alertId": "/subscriptions/<subscription ID>/providers/Microsoft.AlertsManagement/alerts/b9569717-bc32-442f-add5-83a997729330",
"alertRule": "WCUS-R2-Gen2",
"severity": "Sev3",
"signalType": "Metric",
"monitorCondition": "Resolved",
"monitoringService": "Platform",
"alertTargetIDs": [
"/subscriptions/<subscription ID>/resourcegroups/pipelinealertrg/providers/microsoft.compute/virtualmachines/wcus-r2-gen2"
],
"configurationItems": [
"wcus-r2-gen2"
],
"originAlertId": "3f2d4487-b0fc-4125-8bd5-7ad17384221e_PipeLineAlertRG_microsoft.insights_metricAlerts_WCUS-R2-Gen2_-117781227",
"firedDateTime": "2019-03-22T13:58:24.3713213Z",
"resolvedDateTime": "2019-03-22T14:03:16.2246313Z",
"description": "",
"essentialsVersion": "1.0",
"alertContextVersion": "1.0"
},
"alertContext": {
"properties": null,
"conditionType": "SingleResourceMultipleMetricCriteria",
"condition": {
"windowSize": "PT5M",
"allOf": [
{
"metricName": "Percentage CPU",
"metricNamespace": "Microsoft.Compute/virtualMachines",
"operator": "GreaterThan",
"threshold": "25",
"timeAggregation": "Average",
"dimensions": [
{
"name": "ResourceId",
"value": "3efad9dc-3d50-4eac-9c87-8b3fd6f97e4e"
}
],
"metricValue": 7.727
}
]
}
},
"customProperties": {
"Key1": "Value1",
"Key2": "Value2"
}
}
}
}
We will use the Common Alert Schema with Azure Logic Apps in this scenario. The following link provides more information about the Common Alert Schema, including details on the fields:
https://learn.microsoft.com/en-us/azure/azure-monitor/alerts/alerts-common-schema
Creating the Azure Logic App
Creating the Azure Logic App consists of several components, the connectors and the HTML Template.
The Connectors and Corresponding Actions:
HTTP - HTTP
Azure Monitor Logs – Run Query and list results
Variables – Initialize variable.
Variables – Set Variable
Data Operations – Create HTML Table
Data Operations – Parse JSON
Office 365 Outlook – Send Email (V2)
Control – Switch
HTTP Connector
The HTTP connector is a valuable tool for executing API calls, allowing you to acquire additional information to augment the alert content. For instance, you can leverage it to retrieve the Subscription Name using the Subscription ID or to obtain the tenant name using the tenant ID.
You can learn more about the connector here:
Call service endpoints by using HTTP or HTTPS - Azure Logic Apps | Microsoft Learn
Azure Monitor Log
The Azure Monitor Log Connector takes the Search Query obtained from the Common Alert Schema to perform the same Kusto Query. The query is achieved by using the Run Query and List Result Action.
You can learn more about the Azure Monitor Log Connector here:
Azure Monitor Logs - Connectors | Microsoft Learn
The Action used is the following:
Run query and list results
There is also version 2; however, we always recommend proceeding with caution when using something in preview as the SLA/support is limited. In our experience, we have seen certain features completely removed when previewing.
Variables
Variables are an incredible tool in Azure Logic Apps. You can use them to create data types such as integer, float Boolean, string, arrays, and objects. Think of variables like how you think of variables in programming.
After you create a variable, you can perform tasks such as:
Reference the value of the variable elsewhere
Increase or decrease the variable by a constant value, also known as increment and decrement.
Assign a different value to the variable.
Insert or append the variable's value as the last item in a string or array.
Variables exist and are global only within the workflow instance that creates them. Also, they persist across any loop iterations inside a workflow instance. When referencing a variable, use the variable's name as the token, not the action's name, which is the usual way to reference an action's outputs.
In this Logic App, variables will be initialized and set. Use this to store the Subscription Name, ID, Resource Group location of the affected resource, and much more. Use these variables to keep the information you would like to include in an email or will need to use again for future API calls.
The following link provides an overview of the variables:
Create variables to store and pass values - Azure Logic Apps | Microsoft Learn
Data Operations
Azure Logic Apps includes several actions that can be used to perform data operations. These include:
Create a string or JavaScript Object Notation (JSON) object from multiple inputs with different data types. You can then use this string as a single input, rather than repeatedly entering the same information.
Create user-friendly tokens from JavaScript Object Notation (JSON) object properties so you can easily use those properties in your workflow.
Create an HTML or CSV table from an array.
Create an array from another array based on a specified filter or condition.
Create an array based on the specified properties for all the items in another array.
Create a string from all the items in an array and separate those items using a specified character.
Refer to the following documentation for more details on data operations:
Perform operations on data - Azure Logic Apps | Microsoft Learn
For this, Azure Logic App will be creating an HTML table from the results obtained from the Kusto Query.
Office 365 Outlook Connector.
With The Office 365 Outlook connector, you can send an email using the Send an email (V2)
To use this connector, you need a Microsoft Office 365 account for Outlook, where you sign in with a work or school account.
You can learn more about the Office 365 connector here:
Connect to Office 365 Outlook - Azure Logic Apps | Microsoft Learn
The following is a reference for the connector:
Office 365 Outlook - Connectors | Microsoft Learn
Built-in Actions
Azure Logic Apps provides several built-in actions for structuring and controlling the actions in your workflow. These include:
Create the HTML Template:
The design of the alert is driven by the HTML Template you create. This HTML Template should be designed to allow you to add details from the alert and other actions you perform.
Here is an example of an HTML Template we use in this example:
<!DOCTYPE html> <html> <style> .code-block { background-color: #FFFFFF; border: 1px solid #ddd; padding: 20px; border-radius: 4px; overflow-x: auto; } pre { margin: 0; } code { font-family: 'Courier New', monospace; font-size: 14px; } body { font-family: Arial, sans-serif; background-color: #ffffff; margin: 0; padding: 0; } .notification-table-header { width: auto; border-top: none; background: #1470AF; /* Updated color */ font-size: 11.0pt; color: white; font-weight: bold; margin-left: 10px; text-align: left; border: none; border-bottom: solid white 1.5pt; } .notification-table-text { margin-left: 5px; width: 70%; text-align: left; border: none; border-bottom: solid white 1.5pt; background: #EAEAEE; /* Updated color */ font-size: 12.0pt; height: 20.05pt; } .notification-card-footer span { font-size: 12.0pt; color: #7F7F7F; /* Updated color */ } .notification-card-footer p { vertical-align: baseline; } .notification-body { margin: 50px auto; width: 650px; border: 1px solid #000000; background-color: #ffffff; padding: 20px; } .notification-severity { background-color: #4D98A8; color: white; font-size: 16px; text-align: center; } .notification-table { margin-top: 20px; border-collapse: collapse; width: 100%; } .notification-table th, .notification-table td { padding: 8px; border: 1px solid #000; text-align: left; font-size: 12px; } .notification-table th { background-color: #00c5f1; color: white; font-weight: bold; } .expand-btn { display: inline-block; padding: 5px 10px; background-color: #f1f1f1; border: none; color: #000; text-align: center; text-decoration: none; cursor: pointer; margin-top: 20px; font-size: 14px; border-radius: 4px; } .expand-btn:hover { background-color: #ddd; } table.data-table { width: 100%; border-collapse: collapse; margin-top: 20px; } .data-table th, .data-table td { padding: 8px; border: 1px solid #000; text-align: left; } .data-table th { background-color: #1470AF; color: white; font-weight: bold; } </style> <div class="json-block"> <button id="copy-json-button" onclick="copyJsonToClipboard()">Copy JSON</button> <pre> <code class="language-json"> { <body style="background-color: #FFFFFF;"> <table style="width:100%;"> <tr> <td style="padding:0;"> <div align="center"> <table class="notification-body"> <tr style="border: 1px grey; border-top:none;"> <td> <p style='font-size:5.0pt;'> <span> </span> </p> <table style='width:590px;margin:0 auto;border-collapse:collapse;'> <tr style='height:20.05pt'> <td colspan="2" class="notification-table-header" style='width:100%; height:20.05pt'> <p style='text-align:center; font-size:16.0pt;'><b>Severity: [Insert Severity]</b><br /> </p> </td> </tr> <tr class="notification-card-footer"> <td colspan="2"> <p style='text-align:left;'><b>This is some notication Test</b></p> <p style='text-align:left;'>Alert Rule Triggered: <b> [Insert Alert Rule']</b></p> </td> </tr> <tr> <td class="notification-table-header"> <span> Customer Name: </span> </td> <td class="notification-table-text"> [Insert Customer Name']</td> </tr> <tr> <td class="notification-table-header"> <span> Subscription Name: </span> </td> <td class="notification-table-text"> [Insert Customer Subscription Name'] </td> </tr> <tr> <td class="notification-table-header"> <span> Subscription ID: </span> </td> <td class="notification-table-text"> [Insert Customer Subscription']</td> </tr> <tr> <td class="notification-table-header"> <span> Log Type:</span> </td> <td class="notification-table-text">[Insert Monitoring Service'] </td> </tr> <tr> <td class="notification-table-header"> <span> Fired Time:</span> </td> <td class="notification-table-text">[Insert Fired Time'] </td> </tr> <tr> <td class="notification-table-header"> <span> Message:</span> </td> <td class="notification-table-text"> [Insert Alert Description']</td> </tr> <tr> <td class="notification-table-header"> <span> Severity:</span> </td> <td class="notification-table-text">Severity Level: [Insert Severity Level]</td> </tr> <tr> <td class="notification-table-header"> <span> Link to Search Results:</span> </td> <td class="notification-table-text"> <a href= target="_blank"> <span style='font-size:12.0pt;color:blue;'>[Insert Link to Search Results]</span> </a> </td> </tr> <tr> <td class="notification-table-header"> <span> Link to Search Results API:</span> </td> <td class="notification-table-text"> <a href="@{body('Parse_JSON')?['LinkToSearchResultsAPI']}" target="_blank"> <span style='font-size:12.0pt;color:blue;'>[Insert Link to Searh Results API]</span> </a> </td> </tr> <tr> <td class="notification-table-header"> <span> Search Query:</span> </td> <td class="notification-table-text">[Insert Search Query Variable]</td> </tr> <tr class="notification-card-footer"> <td colspan="2"> <p style='text-indent:36.0pt;'> <span style='font-size:0.0pt;'> </span> </p> <p style='text-align:center;'> <span> </span> <br /> </p> </td> </tr> </table> </td> </tr> </table> </div> </td> </tr> </table> [Insert HTML Table],'<table>', '<table class="data-table">'] </body> </html>
Logic App Walkthrough:
We will split these steps into phases. separating the flow into stages to help with testing, especially when using a new trigger/action for the first time.
Setup the Logic App and the HTTP Trigger
In the Azure portal, create a new logic app. In the Search bar at the top of the page, enter Logic App.
On the Logic App page, select Add.
Select the Subscription and Resource group for your logic app.
Set Logic App name. For Plan type, select Consumption.
Select Review + create > Create.
6. Select Go to resource after the deployment is finished.
7. On the Logic Apps Designer page, select When an HTTP request is received.
8. Click on Use sample payload to generate schema.
9. Click Done
10. Next Save the Logic App. After saving, a HTTP Post URL will be generated. You should see something like this:
11. Copy and save this URL; it will be needed when we create the Action Group that will trigger this Logic App.
Setup the Azure Monitor Alert and Action Group for testing
Let's momentarily shift our focus away from the Logic App and direct our attention toward setting up the Azure Monitor Alert and the corresponding Action Group. We suggest establishing an Azure Monitor Log Alert designed for simple triggering. This setup serves the purpose of testing and observing the outcomes derived from implementing the Common Alert Schema.
Define the Kusto Query
This is the Kusto Query we used for our testing; it is triggered when a user fails to sign in to the Azure Portal:
SigninLogs
| where AppDisplayName contains "Azure Portal"
| where ResultType in ("50126", "50020")
| extend OS = DeviceDetail.operatingSystem, Browser = DeviceDetail.browser
| extend StatusCode = tostring(Status.errorCode), StatusDetails = tostring(Status.additionalDetails)
| extend State = tostring(LocationDetails.state), City = tostring(LocationDetails.city)
| summarize StartTime = min(TimeGenerated),
EndTime = max(TimeGenerated),
IPAddresses = makeset(IPAddress)[0],
DistinctIPCount = dcount(IPAddress),
DeviceOS = makeset(OS)[0],
Browser = makeset(Browser)[0],
City = makeset(City)[0],
AttemptCount = count()
by UserDisplayName,
UserPrincipalName,
AppDisplayName,
ResultType,
ResultDescription,
StatusCode,
StatusDetails,
Location,
State,
UserId,
AADTenantId
| extend timestamp = StartTime, AccountCustomEntity = UserPrincipalName
| sort by AttemptCount
Create the Action Group:
In the Basic Section fill the following:
In the Azure Portal, in the Search bar at the top of the page, enter Monitor and click on it when it appears.
Click on Alerts.
Click on Action Groups.
Click on + Create.
In the Basics, set the Subscription, Resource group, and Region accordingly.
In the Basic section, provide a name for the Action group and the display name.
Click on the Actions section and set the Alert type to Logic App/ Secure Webhook/ Webhook. Select Webhook, For the production environment, consider using a Secure Webhook.
Set Name.
Under the Selected Column, click on the Pencil, and a window appears from the right-hand side.
Insert the URI that we obtained from the HTTP Trigger in the last phase.
11. Under Enable the Common Alert Schema click Yes.
12. Click Ok.
13. Click on Review + Create and click Create
Create the Alert Rule
Now that we have the Kusto Query and the Action Group lets create the Alert rule.
In this blog, We won't delve into the process of creating the Azure Monitor Alert. However, the essential steps are as follows:
Include the Kusto Query: When creating the alert rule, make sure to define a relevant Kusto Query that will be used to monitor and filter the data. For testing purposes keep it simple.
Add the Action Group: associated the Action Group that triggers the logic app.
Fill out the Alert Rule Details: Provide all the necessary details for the alert rule, including a meaningful name, description, severity level, and other configuration settings as required.
For guidance in created the Azure Monitor Alerts refer to the following article:
Create Azure Monitor alert rules - Azure Monitor | Microsoft Learn
Configure the Rest of the Logic App.
Define the variables.
Next initialize and set the variables you will use to store the information you want to extract from the Common Alert Schema. In this scenario, we created the following variables:
Affected Resources
Customer Subscription ID
Fired Time
Customer Name
Email Body
Monitoring Service
Alert Rule
Alert Severity
Alert Description
Customer Subscription Name
Affected Resource
This is an array that will be used to populate the Customer Subscription ID.
This array is created by using the following expression: split(triggerBody()?['data']?['essentials']?['alertTargetIDs'][0], '/')
to split string:
/subscriptions/SubscriptionID/resourcegroups/ResourceGroup/providers/microsoft.operationalinsights/workspaces/WorkspaceName
Expression Explained:
The given Logic App expression uses the split function to split a string based on a specified delimiter. Let's break down the expression step by step:
triggerBody(): This function retrieves the entire JSON payload from the Logic App trigger. In this case, it seems that the trigger is receiving a JSON payload.
?: This is the safe navigation operator, which allows the expression to gracefully handle null or missing properties without throwing an error.
['data']: This accesses the "data" property within the JSON payload.
['essentials']: This accesses the "essentials" property within the "data" object.
['alertTargetIDs'][0]: This accesses the first element of the "alertTargetIDs" array within the "essentials" object. It is using [0] to get the first element of the array.
You can get these values from the array; The following tables will indicate which ones can be ignored.
Index | Value | Comments |
---|---|---|
[0] | Empty | Ignore |
[1] | “subscriptions” | Ignore |
[2] | SubsriptionID | Used to get the subscription id. |
[3] | “resourcegroups” | Ignore |
[4] | ResourceGroup | Used to get the resource group of the log analytics workspace that is queried in the alert rule. |
[5] | “providers” | Ignore |
[6] | “Microsoft.operationalinsights” | Ignore |
[7] | “workspace” | Ignore |
[8] | WorkspaceName | The name of the log analytics workspace that is queried in the alert rule. |
The following article provides more information about split:
Customer Subscription ID
This variable is used to store the customer subscription ID. Its obtained by using the previously defined variable Affected Resource.
variables('AffectedResource')[2]
Fired Time
This variable is used to get the time that the alert was fired. This value is obtained by using the following Logic App Expression:
formatDateTime(triggerBody()?['data']?['essentials']?['firedDateTime'],'MMMM-dd, yyyy HH:mm:ss')
Expression Explained:
The given Logic App expression uses the formatDateTime function to format a date and time value obtained from the JSON payload. Let's break down the expression step by step:
triggerBody(): This function retrieves the entire JSON payload from the Logic App trigger. It seems that the trigger is receiving a JSON payload.
?: This is the safe navigation operator, which allows the expression to gracefully handle null or missing properties without throwing an error.
['data']: This accesses the "data" property within the JSON payload.
['essentials']: This accesses the "essentials" property within the "data" object.
['firedDateTime']: This accesses the "firedDateTime" property within the "essentials" object.
The value obtained at this point should be a date and time string in ISO 8601 format, such as "2023-07-12T05:27:38.6313357Z".
6. formatDateTime(..., 'MMMM-dd, yyyy HH:mm:ss'): This part applies the formatDateTime function to the obtained date and time string. It formats the date and time using the custom
format string 'MMMM-dd, yyyy HH:mm:ss'.
The custom format string uses the following format specifiers:
MMMM: Full month name (e.g., "July").
dd: Day of the month (2 digits, e.g., "12").
yyyy: Year (4 digits, e.g., "2023").
HH: Hour (24-hour format, 2 digits, e.g., "05").
mm: Minute (2 digits, e.g., "27").
ss: Second (2 digits, e.g., "38").
The formatDateTime function will convert the ISO 8601 date and time string to the specified format. For example, if the input date and time string is "2023-07-12T05:27:38.6313357Z", the resulting formatted date and time will be "July-12, 2023 05:27:38".
Get additional details:
To get more information about the formatDateTime refer to the following documentation:
formatDateTime - function reference
Customer Name
This variable is manually added for demonstration purposes. The way this variable is populated manually or dynamically using code. Note Customer name is not the same as Customer Tenant. A customer can have multiple tenants.
Email Body
This is a place holder that will later be filled with the HTML template previously created.
Monitoring Service
This variable serves a crucial role in identifying the monitoring service or solution responsible for generating the alert. Its value is pivotal in determining the specific fields present in the alert context.
Within this Logic App, we leverage this variable as part of a Switch Control, allowing me to effectively handle alerts originating from diverse monitoring services. As mentioned earlier, the alert context varies depending on the monitoring service or solution that triggered the alert.
For an in-depth understanding of each monitoring service or solution's alert context, we have prepared a comprehensive article detailing their respective components and attributes. This article will help users grasp the nuances and peculiarities associated with each monitoring service, allowing for better contextualization and interpretation of alerts.
Common Alert Schema for Azure Monitor alerts - Azure Monitor | Microsoft Learn
Alert Rule
This variable is used to store the Alert Rule that triggered the Logic App.
Alert Severity
This variable is used to store the Alert Severity associated with the Alert Rule triggered.
Alert Description
This variable is used to store the Alert Rule Description. If the description is left blank when creating the Azure Monitor Alert, this variable will be an empty string.
Customer Subscription Name
If you already have the Customer Azure Subscription ID, you can leverage an API call to retrieve the name of the Customer Azure Subscription. This provides a convenient way to quickly identify both the customer’s subscription name and the impacted customer subscription ID.
APIs can offer valuable insights by providing access to various types of information. For example, you can obtain the Tenant ID and Tenant Name associated with the Subscription, which becomes particularly useful when a single customer has multiple tenants.
It is essential to note that the method of authentication for API calls may vary depending on the specific calls you are making. For instance, to obtain the Customer Subscription Name, the Logic App must have either a System Assigned Identity or a User Assigned Identity assigned to it. This identity is then granted, at a minimum, the Reader role for the customer subscription.
By effectively utilizing API calls and appropriate authentication methods, you can gather crucial information about customer subscriptions and related resources, enabling streamlined monitoring and management processes for your Azure environment.
Define the Switch Control:
In this next step, we use a Switch Control, this may not be necessary if you know precisely what monitoring solution or service that will trigger this Azure Logic App.
In this example, we set up nine possible cases to capture each possible Monitoring solution or service. Again this is necessary as the Alert Context changes depending on the monitoring solution or service if you are aware of what type of alert will trigger this Azure Logic App no need to create multiple workspaces.
Generate the Email
Parse JSON
I use this to parse the Alert Context, although it’s not required. This makes it easier to get details of the alert.
Run Query and list results
This part is optional. However, we include it in the alert to save time from having to click the Link to get to the results query. This returns an array of results. The results from this action will be passed into the data operation called Create HTML Table.
Azure Monitor Logs - Connectors | Microsoft Learn
Create HTML Table
This action will take the results from the Kusto Query and generate an HTML table. It should be filled in as follows:
From : Value
Columns: Automatic or Custom. If you do custom, it will limit the reusability of this logic app. This is because you will need to know the data the alert will be working with ahead of time. Suppose you wish to make changes to the column without having to create custom headers. This can be achieved by modifying the Kusto query itself and renaming the columns using the commands project.
This Action does not produce a stylized HTML Table. Instead, you need to ensure that the HTML template you are using can apply the CSS to the HTML Table. In this logic, we approach it by first declaring the CSS style. Then we modify the results returned from the Create HTML Table Action.
Using this following power automate expression:
replace(body('Create_HTML_table'),'<table>', '<table class="data-table">')
The purpose of this expression is to add a CSS class named "data-table" to the existing HTML table. The CSS class can be used for styling or applying specific formatting to the table. The resulting modified HTML content will have the updated <table> tag with the added class attribute.
For example, if the original HTML content is:
<table> <!-- Table content here --> </table>
The replace function will modify it to:
<table class="data-table"> <!-- Table content here --> </table>
By using this expression, you can dynamically apply a class to an HTML table generated by the "Create_HTML_table" action, providing flexibility in styling and presentation within your Logic App workflow.
You can learn more about this action here:
Perform operations on data - Azure Logic Apps | Microsoft Learn
You can learn more operators in Kusto Query that can be used to rename columns:
Project operator | Microsoft Learn
extend operator | Microsoft Learn
Set Email Body
This action is where we paste HTML Template. Within this HTML Template, we can begin inserting the previously collected information.
Here we have inserted the Customer Name, Customer Subscription Name, and Customer Subscription ID
Send an Email (V2)
Lastly, we use the Send an Email (V2) action.
At this point, we simply past the Email Body into the body of the email:
When this Azure Logic App is triggered when the Azure monitor alert is triggered, you will now receive an email with more details.
In Conclusion
The aim of this blog is to exemplify the utilization of the Common Alert Schema for extracting additional information from an Azure Monitor Alert. Specifically, we can gain more information to help us discern the customer associated with the alert. To enhance the quality of email notifications, the incorporation of SendGrid can be explored. In forthcoming entries, we will expand upon this topic with a collection of further illustrative examples.