Loading...

Draw.io Azure infrastructure diagrams through code like an artist

Draw.io Azure infrastructure diagrams through code like an artist

Introduction

 

In this article we will see how to create an Azure diagram to reveal all the dependencies between Azure App Services, their Application Insights and finally their workspace-based Log Analytics Workspaces.

 

The use case consist in:

 

  1. auditing the current configuration on Azure through a PowerShell script,
  2. export the current infrastructure set up on a CSV Draw.io readable file,
  3. observe a work of art.

 

Jamesdld23_0-1709191560621.jpeg

 

 

Concept

 

To make this piece of art possible you should have a clear idea of the following concept.

 

  1. Azure resource dependencies: An App Service or Function App can send logs to an Application Insights and Application Insights can send logs to a Log Analytics workspace. This refers to the concept of Workspace-based Application Insights resources.
  2. Draw.io is a free diagram software that permits to insert diagram from specially formatted CSV Data as explained in the following blog.

 

We can now move on to the next chapter which consists of creating a script that will scan our Infrastructure and write to the CSV in draw.io format.

 

 

Script

 

The following PowerShell script will analyze your App Services configuration based on which ones have these tags and export its results to a local file.

 

 

$AzureTagToFilterOn = @{ "env" = "dev" } $FileForDrawIo = "draw.io.export.txt"

 

 

There are 2 main tips on the script you should understand:

 

  1. The Draw.io “styles” block points out to existing Draw.io shapes, you can print their code by selecting an existing shape, then press Ctrl+E on Windows or Cmd+E on macOS.
  2. You can create multiple connections between your CSV rows with their own properties (labels, line style, etc…).

The complete script:

 

 

#region variable $SubscriptionName = "Your Azure Subscription Name" $AzureTagToFilterOn = @{ "env" = "dev" } $FileForDrawIo = "draw.io.export.txt" $DrawIoExport = @() $contentToAdd = @" ## Azure Application Insights depedencies. ## Node label with placeholders and HTML. ## Default is '%name_of_first_column%'. # # label: %name%<br><i style="color:gray;">%type%</i><br> # ## Shapes and their styles # stylename: type # styles: {"application insights": "aspect=fixed;html=1;points=[];align=center;image;fontSize=15;image=img/lib/azure2/management_governance/Application_Insights.svg;",\ # "functionapp": "aspect=fixed;html=1;points=[];align=center;image;fontSize=15;image=img/lib/azure2/iot/Function_Apps.svg;",\ # "log analytics workspaces": "aspect=fixed;html=1;points=[];align=center;image;fontSize=15;image=img/lib/azure2/management_governance/Log_Analytics_Workspaces.svg;",\ # "app": "aspect=fixed;html=1;points=[];align=center;image;fontSize=12;image=img/lib/azure2/app_services/App_Services.svg;"} ## Connections between rows ("from": source colum, "to": target column). ## Label, style and invert are optional. Defaults are '', current style and false. # connect: {"from": "application_insights", "to": "name", "label": "logs", \ # "style": "curved=1;endArrow=blockThin;endFill=1;fontSize=11;"} # connect: {"from": "log_analytics_workspaces", "to": "name", "style": "curved=1;fontSize=11;"} # # ignore: application_insights,log_analytics_workspaces # layout: verticalflow # ## ---- CSV below this line. First line are column names. ---- "@ Set-Content $FileForDrawIo $contentToAdd Add-Content $FileForDrawIo "name,resource_group,type,application_insights,log_analytics_workspaces" #endregion #region function Function draw_io_csv { [CmdletBinding()] Param ( [Parameter(Mandatory = $true, ValueFromPipeline = $true)][String] $name, [Parameter(Mandatory = $true, ValueFromPipeline = $true)][String] $resource_group, [Parameter(Mandatory = $true, ValueFromPipeline = $true)][String] $type, [Parameter(Mandatory = $false, ValueFromPipeline = $true)][String] $application_insights, [Parameter(Mandatory = $false, ValueFromPipeline = $true)][String] $log_analytics_workspaces ) Process { $private:tableObj = New-Object PSObject $tableObj | Add-Member -Name name -MemberType NoteProperty -Value $name $tableObj | Add-Member -Name resource_group -MemberType NoteProperty -Value $resource_group $tableObj | Add-Member -Name type -MemberType NoteProperty -Value $type $tableObj | Add-Member -Name application_insights -MemberType NoteProperty -Value $application_insights $tableObj | Add-Member -Name log_analytics_workspaces -MemberType NoteProperty -Value $log_analytics_workspaces return $tableObj } } #endregion #region action ## connectivity $AzureRmContext = Get-AzSubscription -SubscriptionName $SubscriptionName | Set-AzContext -ErrorAction Stop Select-AzSubscription -Name $SubscriptionName -Context $AzureRmContext -Force -ErrorAction Stop ## audit $ResourceGroups = Get-AzResourceGroup -Tag $AzureTagToFilterOn | Select-Object ResourceGroupName $AllAppInsights = Get-AzResource -ResourceType "microsoft.insights/components" -ExpandProperties foreach ($ResourceGroup in $ResourceGroups) { Write-Host "Working on Resource Group Name [$($ResourceGroup.ResourceGroupName)]" -ForegroundColor Cyan $WebApps = Get-AzWebApp -ResourceGroupName $ResourceGroup.ResourceGroupName | Select-Object ResourceGroup, Name foreach ($WebAppResource in $WebApps) { Write-Host "Working on Web App [$($WebAppResource.Name)]" -ForegroundColor Cyan $WebApp = Get-AzWebApp -ResourceGroupName $WebAppResource.ResourceGroup -Name $WebAppResource.Name $AppInsightsInstrumentationKey = $WebApp.SiteConfig.AppSettings.GetEnumerator() | Where-Object {$_.name -eq "APPINSIGHTS_INSTRUMENTATIONKEY"} $AppInsightsProperties = $AllAppInsights | Select-Object -ExpandProperty Properties | Select-Object Name, InstrumentationKey, WorkspaceResourceId | Where-Object {$_.InstrumentationKey -eq $AppInsightsInstrumentationKey.Value} if($AppInsightsProperties) { if($AppInsightsProperties.WorkspaceResourceId) { Write-Host "Export the configuration of the Log Analytics Workspace [$($AppInsightsProperties.WorkspaceResourceId.split("/")[-1])] connected to the App [$($WebAppResource.Name)]" $LogAnalyticsWorkspacesName = $AppInsightsProperties.WorkspaceResourceId.split("/")[-1] $DrawIoExport += draw_io_csv -name $AppInsightsProperties.WorkspaceResourceId.split("/")[-1] ` -resource_group $AppInsightsProperties.WorkspaceResourceId.split("/")[-5] ` -type "log analytics workspaces" ` -application_insights "" ` -log_analytics_workspaces "" }else{ $LogAnalyticsWorkspacesName = "" } $AppInsightsId = $($AllAppInsights | Where-Object {$_.Name -like $AppInsightsProperties.Name}).Id $AppInsightsName = $($AppInsightsId.Split("/")[-1]) Write-Host "Export the configuration of the Application Insights [$($AppInsightsId.split("/")[-1])] connected to the App [$($WebAppResource.Name)]" $DrawIoExport += draw_io_csv -name $AppInsightsId.split("/")[-1] ` -resource_group $AppInsightsId.split("/")[-5] ` -type "application insights" ` -application_insights "" ` -log_analytics_workspaces $LogAnalyticsWorkspacesName }else{ $AppInsightsName = "" } Write-Host "Export the configuration of the App [$($WebAppResource.Name)]" $DrawIoExport += draw_io_csv -name $WebApp.Name ` -resource_group $WebApp.ResourceGroup ` -type $WebApp.Kind.Split(",")[0] ` -application_insights $AppInsightsName ` -log_analytics_workspaces "" } } #endregion #region export foreach($Line in $DrawIoExport | Select-Object -Unique -Property name, resource_group, type, application_insights, log_analytics_workspaces){ Add-Content $FileForDrawIo "$($Line.name),$($Line.resource_group),$($Line.type),$($Line.application_insights),$($Line.log_analytics_workspaces)".ToLower() } #endregion

 

 

 

Rendering

 

From Draw.io select Arrange > Insert > Advanced > CSV.

 

Jamesdld23_1-1709191674751.png

 

 

 

Paste your formatting information and CSV data into the large text field, overwriting the example.

 

Jamesdld23_2-1709191674495.png

 

 

The following screenshot illustrates a diagram generated by the PowerShell script.

 

Jamesdld23_3-1709191674490.png

 

 

Conclusion

 

We saw in this demo how to draw a script-based Azure App Service oriented diagram. This methodology has no limits and DALL-E knows it, would you defeat it ?

 

See You in the Cloud

Jamesdld

Published on:

Learn more
Azure Developer Community Blog articles
Azure Developer Community Blog articles

Azure Developer Community Blog articles

Share post:

Related posts

Announcing Azure MCP Server 1.0.0 Stable Release – A New Era for Agentic Workflows

Today marks a major milestone for agentic development on Azure: the stable release of the Azure MCP Server 1.0! The post Announcing Azure MCP ...

1 day ago

From Backup to Discovery: Veeam’s Search Engine Powered by Azure Cosmos DB

This article was co-authored by Zack Rossman, Staff Software Engineer, Veeam; Ashlie Martinez, Staff Software Engineer, Veeam; and James Nguye...

1 day ago

Azure SDK Release (October 2025)

Azure SDK releases every month. In this post, you'll find this month's highlights and release notes. The post Azure SDK Release (October 2025)...

2 days ago

Microsoft Copilot (Microsoft 365): [Copilot Extensibility] No-Code Publishing for Azure AI Foundry Agents to Microsoft 365 Copilot Agent Store

Developers can now publish Azure AI Foundry Agents directly to the Microsoft 365 Copilot Agent Store with a simplified, no-code experience. Pr...

2 days ago

Azure Marketplace and AppSource: A Unified AI Apps and Agents Marketplace

The Microsoft AI Apps and Agents Marketplace is set to transform how businesses discover, purchase, and deploy AI-powered solutions. This new ...

5 days ago

Episode 413 – Simplifying Azure Files with a new file share-centric management model

Welcome to Episode 413 of the Microsoft Cloud IT Pro Podcast. Microsoft has introduced a new file share-centric management model for Azure Fil...

6 days ago

Bringing Context to Copilot: Azure Cosmos DB Best Practices, Right in Your VS Code Workspace

Developers love GitHub Copilot for its instant, intelligent code suggestions. But what if those suggestions could also reflect your specific d...

7 days ago

Build an AI Agentic RAG search application with React, SQL Azure and Azure Static Web Apps

Introduction Leveraging OpenAI for semantic searches on structured databases like Azure SQL enhances search accuracy and context-awareness, pr...

7 days ago

Announcing latest Azure Cosmos DB Python SDK: Powering the Future of AI with OpenAI

We’re thrilled to announce the stable release of Azure Cosmos DB Python SDK version 4.14.0! This release brings together months of innov...

9 days ago
Stay up to date with latest Microsoft Dynamics 365 and Power Platform news!
* Yes, I agree to the privacy policy