Sovereign Cloud Architectuur Voor Azure In De Nederlandse Publieke Sector

šŸ’¼ Management Samenvatting

Een sovereign cloud architectuur vormt de technische en organisatorische basis voor het realiseren van digitale soevereiniteit binnen Azure-omgevingen. Voor Nederlandse overheidsorganisaties die werken onder de BIO, AVG en NIS2 betekent dit dat cloudarchitectuur expliciet wordt ontworpen met strategische controle, onafhankelijkheid en compliance als uitgangspunten. Een sovereign cloud architectuur gaat verder dan alleen technische configuratie: het omvat architectuurprincipes, governance-structuren, beveiligingslagen, monitoring- en auditprocessen die gezamenlijk bijdragen aan het behoud van strategische controle over kritieke gegevens en systemen.

Aanbeveling
ONTWERP EN IMPLEMENTEER EEN SOVEREIGN CLOUD ARCHITECTUUR VOOR UW AZURE-OMGEVING
Risico zonder
High
Risk Score
9/10
Implementatie
200u (tech: 120u)
Van toepassing op:
āœ“ Azure Tenant
āœ“ Azure Resources
āœ“ Publieke Sector
āœ“ Overheidsorganisaties
āœ“ Kritieke Infrastructuur

Zonder een expliciet ontworpen sovereign cloud architectuur ontstaat er een risico dat Azure-omgevingen organisch groeien zonder duidelijke focus op digitale soevereiniteit. Dit kan leiden tot situaties waarin resources verspreid zijn over verschillende regio's zonder strategische afweging, waarin afhankelijkheden van niet-EU jurisdicties onvoldoende worden beheerst, en waarin architectuurkeuzes niet bijdragen aan het behoud van strategische controle. Voor Nederlandse overheidsorganisaties die kritieke infrastructuur beheren of gevoelige gegevens verwerken, kan het ontbreken van een sovereign cloud architectuur leiden tot vragen van toezichthouders over de mate waarin de organisatie daadwerkelijk controle heeft over haar cloudomgeving. Bovendien ontstaat er zonder duidelijke architectuurrichtlijnen een risico dat nieuwe projecten en workloads niet consistent worden uitgerold volgens soevereiniteitsprincipes, wat op termijn leidt tot technische schuld en complexiteit die moeilijk te corrigeren is.

PowerShell Modules Vereist
Primary API: Azure API, Azure Resource Manager, Azure Policy
Connection: Connect-AzAccount
Required Modules: Az.Accounts, Az.Resources, Az.Policy, Az.ResourceGraph

Implementatie

Dit artikel beschrijft hoe Nederlandse publieke organisaties een sovereign cloud architectuur ontwerpen en implementeren binnen Azure. We beginnen met de uitleg van het concept sovereign cloud architectuur en de relatie met digitale soevereiniteit, gevolgd door architectuurprincipes en ontwerppatronen die bijdragen aan strategische controle. Vervolgens gaan we in op praktische implementatiestappen, zoals het ontwerpen van management group-hiƫrarchieƫn met soevereiniteit als uitgangspunt, het configureren van landing zones die automatisch compliance en soevereiniteit afdwingen, het implementeren van beveiligingslagen die bijdragen aan onafhankelijkheid, en het opzetten van monitoring- en governance-processen. In de secties over architectuurpatronen, beveiliging en governance laten we zien hoe je met behulp van een PowerShell-script periodiek kunt toetsen of de Azure-architectuur voldoet aan sovereign cloud principes en hoe je bevindingen vertaalt naar architectuurverbeteringen en strategische beslissingen. Het doel is een praktisch toepasbaar raamwerk dat cloudarchitecten, CISO's en strategische adviseurs in staat stelt om een sovereign cloud architectuur niet alleen te ontwerpen, maar ook aantoonbaar te implementeren en te verankeren in de bredere cloudstrategie.

Het concept van een sovereign cloud architectuur

Een sovereign cloud architectuur is een cloudarchitectuur die expliciet is ontworpen om digitale soevereiniteit te ondersteunen: het vermogen van een organisatie om strategische controle te behouden over haar gegevens, systemen en digitale infrastructuur, onafhankelijk van externe invloeden of jurisdicties. Voor Nederlandse overheidsorganisaties betekent dit dat de architectuur vanaf het begin wordt ontworpen met principes zoals EU-first deployment, strategische controle, transparantie en verantwoording, en minimale afhankelijkheid van niet-EU jurisdicties. Een sovereign cloud architectuur verschilt van een standaard cloudarchitectuur doordat soevereiniteitsprincipes niet achteraf worden toegevoegd, maar integraal onderdeel zijn van het ontwerp.

De architectuurprincipes van een sovereign cloud omvatten verschillende dimensies. Ten eerste gaat het om geografische controle: resources worden primair uitgerold in EU-regio's die voldoen aan de EU Data Boundary, met expliciete documentatie en goedkeuring voor eventuele uitzonderingen. Ten tweede gaat het om technische controle: de organisatie heeft volledige controle over encryptie, toegangsbeveiliging, netwerkconfiguratie en beveiligingslagen, zonder afhankelijkheid van standaardconfiguraties die mogelijk niet voldoen aan soevereiniteitseisen. Ten derde gaat het om operationele controle: de organisatie kan onafhankelijk opereren zonder externe druk, met heldere exit-strategieƫn en minimale vendor lock-in. Ten vierde gaat het om juridische controle: gegevens en systemen vallen primair onder Europees en Nederlands rechtskader, met minimale blootstelling aan extraterritoriale bevoegdheden.

Voor Nederlandse overheidsorganisaties wordt een sovereign cloud architectuur gevormd door verschillende wet- en regelgevingskaders. De Baseline Informatiebeveiliging Overheid (BIO) benadrukt beheersing van uitbesteding, contractmanagement en ketenverantwoordelijkheid, waarbij architectuurkeuzes moeten bijdragen aan aantoonbare controle over gegevensverwerking en systemen. De NIS2-richtlijn versterkt deze focus door te eisen dat operators van essentiƫle diensten systematisch risico's in de toeleveringsketen beoordelen en documenteren, waarbij architectuur een belangrijke mitigerende maatregel kan zijn. De AVG stelt daarnaast eisen aan doorgifte van persoonsgegevens aan derde landen, waarbij architectuurkeuzes moeten bijdragen aan het waarborgen dat persoonsgegevens binnen de EER blijven of dat passende waarborgen zijn getroffen.

Een veelvoorkomend misverstand is dat een sovereign cloud architectuur automatisch wordt bereikt door alleen resources in EU-regio's uit te rollen. In werkelijkheid omvat een sovereign cloud architectuur veel meer: het gaat om het ontwerpen van management group-hiƫrarchieƫn die soevereiniteitsprincipes afdwingen, het implementeren van landing zones die automatisch compliance en beveiliging borgt, het configureren van netwerkarchitecturen die bijdragen aan isolatie en controle, het opzetten van monitoring- en auditprocessen die aantoonbaar maken dat soevereiniteitsprincipes worden nageleefd, en het verankeren van governance-structuren die ervoor zorgen dat nieuwe projecten en workloads consistent worden uitgerold volgens soevereiniteitsprincipes. Dit artikel helpt organisaties om deze vertaalslag gestructureerd te maken en een sovereign cloud architectuur te verankeren in de bredere cloudstrategie en risicobeheersing.

Architectuurprincipes voor sovereign cloud

Een effectieve sovereign cloud architectuur begint bij heldere architectuurprincipes die richting geven aan ontwerpbeslissingen, implementatiestappen en beheerprocessen. Het eerste principe is 'sovereignty by design': nieuwe cloudinitiatieven worden standaard ontworpen met soevereiniteitsprincipes als uitgangspunt, waarbij expliciet wordt vastgelegd welke architectuurkeuzes bijdragen aan strategische controle en welke afwegingen worden gemaakt. Dit principe voorkomt dat soevereiniteit achteraf moet worden toegevoegd en zorgt ervoor dat architectuurkeuzes vanaf het begin bijdragen aan het behoud van controle en onafhankelijkheid.

Het tweede principe is 'defense in depth voor soevereiniteit': soevereiniteitsmaatregelen worden niet alleen afgedwongen via ƩƩn technische laag, maar via meerdere complementaire maatregelen die elkaar versterken. Dit omvat bijvoorbeeld Azure Policies die regionale restricties afdwingen, resource locks die voorkomen dat resources onbedoeld worden verplaatst, netwerkisolatie die bijdragen aan controle, encryptie die bijdragen aan onafhankelijkheid, en monitoring- en auditprocessen die aantoonbaar maken dat soevereiniteitsprincipes worden nageleefd. Door meerdere lagen te combineren, wordt de kans op afwijkingen verkleind en ontstaat er robuustheid in de architectuur.

Het derde principe is 'gecontroleerde autonomie': ontwikkelteams en business units krijgen autonomie om workloads uit te rollen, maar binnen duidelijke kaders die soevereiniteitsprincipes afdwingen. Dit betekent dat standaard deployment-templates, Infrastructure as Code-sjablonen en landing zones automatisch soevereiniteitsprincipes borgt, zodat teams niet handmatig hoeven na te denken over regio's, encryptie of toegangsbeveiliging. Door autonomie te combineren met geautomatiseerde guardrails, ontstaat er een balans tussen flexibiliteit en controle die bijdraagt aan zowel productiviteit als soevereiniteit.

Binnen Azure vertaalt dit zich naar een architectuur waarin management groups, subscriptions en landing zones zijn ontworpen met soevereiniteit als uitgangspunt. De management group-hiƫrarchie wordt gebruikt om soevereiniteitsprincipes centraal af te dwingen via Azure Policies, waarbij verschillende lagen kunnen worden gebruikt voor verschillende dataclassificaties of compliance-eisen. Landing zones worden ontworpen als standaardomgevingen die automatisch compliance en beveiliging borgt, inclusief regionale restricties, encryptie, netwerkisolatie en monitoring. Door Infrastructure as Code te gebruiken voor alle deployments, kan de architectuur worden vastgelegd en geborgd in code, in plaats van overgelaten aan handmatige keuzes in de portal.

Architectuurprincipes moeten bovendien worden verankerd in governance: besluitvormingsstructuren, richtlijnen en standaarddocumentatie. Dat betekent dat elk nieuw cloudproject een expliciete sovereign cloud architectuur-paragraaf in zijn architectuurdossier krijgt, waarin wordt beschreven welke architectuurprincipes worden toegepast, welke regio's worden gebruikt, welke beveiligingslagen worden geĆÆmplementeerd en hoe soevereiniteit wordt gemonitord en geaudit. Deze informatie wordt hergebruikt in DPIA's, NIS2-risicobeoordelingen en strategische besluitvorming. Door de gekozen principes te koppelen aan meetbare criteria – bijvoorbeeld een maximaal percentage resources buiten EU-regio's, een verplichte lijst van toegestane regio's of een minimum soevereiniteitsscore – ontstaat een basis voor geautomatiseerde controles en continue monitoring.

Implementatiepatronen en architectuurontwerp

Gebruik PowerShell-script sovereign-cloud-architecture.ps1 (functie Invoke-Implementation) – Gebruik dit PowerShell-script om de sovereign cloud architectuur te analyseren, management group-hiĆ«rarchieĆ«n te beoordelen, landing zones te evalueren en architectuurverbeteringen te identificeren..

De implementatie van een sovereign cloud architectuur start met het ontwerpen van een management group-hiërarchie die soevereiniteitsprincipes centraal afdwingt. De hiërarchie wordt opgebouwd met verschillende lagen: een root management group voor centrale policies en governance, management groups per dataclassificatie of compliance-eis (bijvoorbeeld 'Geclassificeerd', 'Persoonsgegevens', 'Publiek'), en management groups per business unit of project. Azure Policies worden geïmplementeerd op management group-niveau om automatisch regionale restricties, encryptie-eisen, netwerkconfiguratie en beveiligingslagen af te dwingen. Door policies centraal te definiëren en te verspreiden via de hiërarchie, ontstaat er consistentie in de architectuur zonder dat elk project handmatig moet worden geconfigureerd.

Landing zones vormen een cruciaal onderdeel van een sovereign cloud architectuur omdat zij standaardomgevingen bieden die automatisch compliance en beveiliging borgt. Een landing zone is een vooraf geconfigureerde Azure-omgeving die bestaat uit een subscription, resource groups, netwerkconfiguratie, beveiligingslagen en monitoring. Voor een sovereign cloud architectuur worden landing zones ontworpen met expliciete focus op soevereiniteit: zij gebruiken alleen goedgekeurde EU-regio's, implementeren automatisch encryptie en toegangsbeveiliging, configureren netwerkisolatie volgens zero trust-principes, en stellen monitoring- en auditprocessen in die aantoonbaar maken dat soevereiniteitsprincipes worden nageleefd. Door Infrastructure as Code te gebruiken voor landing zones, kunnen deze worden hergebruikt en consistent worden uitgerold voor nieuwe projecten.

Netwerkarchitectuur vormt een essentieel onderdeel van een sovereign cloud architectuur omdat het bijdraagt aan isolatie, controle en onafhankelijkheid. Een sovereign cloud netwerkarchitectuur omvat verschillende componenten: hub-and-spoke-topologieën die centrale netwerkdiensten bieden terwijl workloads geïsoleerd blijven, private endpoints die voorkomen dat data over het publieke internet gaat, Virtual Network-peering die gecontroleerde connectiviteit biedt tussen workloads, en Network Security Groups die granular toegangscontrole afdwingen. Door netwerkarchitectuur expliciet te ontwerpen met soevereiniteitsprincipes in het achterhoofd, ontstaat er een basis voor gecontroleerde en onafhankelijke operatie.

Het PowerShell-script sovereign-cloud-architecture.ps1 ondersteunt deze implementatie door automatisch te analyseren of de Azure-architectuur voldoet aan sovereign cloud principes. Het script maakt verbinding met Azure via Connect-AzAccount, haalt management group-hiƫrarchieƫn op, analyseert subscriptions en resources op hun compliance met soevereiniteitsprincipes, en controleert of landing zones correct zijn geconfigureerd. De uitvoer bevat zowel een totaalscore per tenant als een gedetailleerd overzicht per management group, subscription en resource, waardoor teams gericht acties kunnen uitzetten naar de eigenaar van de betreffende omgeving. Het script kan herhaaldelijk worden gedraaid na architectuurwijzigingen om te verifiƫren dat de verwachte architectuur inderdaad aanwezig is en dat soevereiniteitsprincipes worden nageleefd.

Beveiligingslagen en controlemechanismen

Een sovereign cloud architectuur vereist meerdere beveiligingslagen die gezamenlijk bijdragen aan strategische controle en onafhankelijkheid. De eerste laag is encryptie: alle data-at-rest en data-in-transit worden versleuteld met door de organisatie beheerde sleutels, waarbij Azure Key Vault wordt gebruikt voor centrale sleutelbeheer. Customer-managed keys (CMK) worden gebruikt in plaats van Microsoft-managed keys om ervoor te zorgen dat de organisatie volledige controle heeft over encryptie en dat sleutels niet kunnen worden ontsleuteld zonder expliciete toestemming. De tweede laag is toegangsbeveiliging: Azure Active Directory wordt gebruikt voor identiteits- en toegangsbeheer, met Conditional Access policies die risicogebaseerde toegangscontrole afdwingen, Privileged Identity Management voor just-in-time toegang tot beheerfuncties, en Role-Based Access Control voor granular resource-toegang.

De derde laag is netwerkbeveiliging: Virtual Networks worden gebruikt voor isolatie, Network Security Groups voor granular toegangscontrole, Azure Firewall voor gecentraliseerde netwerkbeveiliging, en Private Endpoints voor beveiligde connectiviteit naar PaaS-diensten zonder blootstelling aan het publieke internet. De vierde laag is monitoring en detectie: Azure Monitor wordt gebruikt voor centrale logging en monitoring, Azure Sentinel voor security information and event management (SIEM), en Azure Security Center voor continue beveiligingsbeoordeling en aanbevelingen. Door meerdere beveiligingslagen te combineren, ontstaat er defense in depth die bijdraagt aan zowel beveiliging als soevereiniteit.

Controlemechanismen vormen een essentieel onderdeel van een sovereign cloud architectuur omdat zij aantoonbaar maken dat beveiligingslagen effectief zijn en dat soevereiniteitsprincipes worden nageleefd. Azure Policies worden gebruikt om automatisch te controleren of resources voldoen aan beveiligingseisen, zoals encryptie, toegangsbeveiliging en netwerkconfiguratie. Resource locks worden gebruikt om te voorkomen dat resources onbedoeld worden gewijzigd of verwijderd, wat bijdraagt aan stabiliteit en controle. Monitoring- en auditprocessen worden gebruikt om continu te toetsen of beveiligingslagen correct functioneren en of er afwijkingen zijn die moeten worden gecorrigeerd. Door controlemechanismen te koppelen aan governance-processen, ontstaat er een basis voor continue verbetering en aantoonbare compliance.

Monitoring, governance en continue verbetering

Gebruik PowerShell-script sovereign-cloud-architecture.ps1 (functie Invoke-Monitoring) – Voert een periodieke controle uit op de Azure-architectuur en rapporteert of deze voldoet aan sovereign cloud principes, met ondersteuning voor een lokale debugmodus zonder cloudverbinding..

Monitoring van een sovereign cloud architectuur kan niet worden beperkt tot eenmalige configuratiecontroles. Nieuwe projecten, uitbreidingen en wijzigingen in de Azure-omgeving kunnen ertoe leiden dat architectuurkeuzes alsnog afwijken van soevereiniteitsprincipes, ondanks de ingestelde policies en guardrails. Een volwassen monitoringaanpak combineert daarom geautomatiseerde controles met vaste rapportagemomenten en strategische beoordelingen. Voor Azure betekent dit dat er periodiek – bijvoorbeeld maandelijks of per kwartaal – een architectuuranalyse wordt uitgevoerd die toetst of management groups, subscriptions, landing zones en resources voldoen aan sovereign cloud principes. Op basis daarvan kan worden vastgesteld welk percentage van de omgeving voldoet aan soevereiniteitsprincipes en waar afwijkingen of verbetermogelijkheden optreden.

Governance vormt de basis voor effectieve sovereign cloud architectuur omdat het richting geeft aan besluitvorming, beleidsvorming en implementatie. Een volwassen governance-structuur omvat verschillende componenten: besluitvormingsstructuren die bepalen wie verantwoordelijk is voor het opstellen en goedkeuren van architectuurprincipes, richtlijnen die beschrijven welke architectuurpatronen zijn goedgekeurd en welke processen moeten worden gevolgd, standaarddocumentatie die wordt gebruikt voor architectuurdossiers, DPIA's en contractdossiers, en governance-processen die uitzonderingen beoordelen en goedkeuren. Voor Nederlandse overheidsorganisaties is het belangrijk om deze governance-structuur te koppelen aan bredere governance-kaders, zoals informatiebeveiligingsbeleid, privacybeleid en contractmanagement.

Continue verbetering is een essentieel aspect van een volwassen sovereign cloud architectuur omdat het ervoor zorgt dat architectuurprincipes effectief blijven en dat nieuwe eisen en ontwikkelingen worden geadresseerd. Continue verbetering omvat het regelmatig evalueren van architectuurkeuzes, het identificeren van verbetermogelijkheden, het implementeren van verbeteringen en het monitoren van de effectiviteit van verbeteringen. Dit kan bijvoorbeeld betekenen dat management group-hiƫrarchieƫn worden verfijnd op basis van ervaringen, dat landing zones worden verbeterd om beter aan te sluiten bij soevereiniteitsprincipes, of dat policies worden aangepast om nieuwe risico's te adresseren. Door continue verbetering te koppelen aan monitoring en governance, ontstaat er een basis voor evolutie en volwassenheid van de sovereign cloud architectuur.

Compliance & Frameworks

Automation

Gebruik het onderstaande PowerShell script om deze security control te monitoren en te implementeren. Het script bevat functies voor zowel monitoring (-Monitoring) als remediation (-Remediation).

PowerShell
<# ================================================================================ AZURE POWERSHELL SCRIPT - Nederlandse Baseline voor Veilige Cloud ================================================================================ .SYNOPSIS Analyse van sovereign cloud architectuur voor Azure-omgevingen .DESCRIPTION Voert een analyse uit op: - Management group-hiƫrarchieƫn en hun structuur - Subscriptions en hun compliance met soevereiniteitsprincipes - Resources en hun regio's - Landing zones en hun configuratie - Azure Policies die soevereiniteitsprincipes afdwingen - Resource locks voor kritieke workloads - Netwerkarchitectuur en isolatie Het script ondersteunt twee gebruiksscenario's: - Productie: verbinding met Azure om daadwerkelijke architectuurgegevens op te halen - Lokale debugmodus: synthetische testdata genereren zonder cloudverbinding Dit script sluit inhoudelijk aan op het artikel 'Sovereign Cloud Architectuur voor Azure in de Nederlandse Publieke Sector'. .NOTES Filename: sovereign-cloud-architecture.ps1 Author: Nederlandse Baseline voor Veilige Cloud Version: 1.0 Related JSON: content/azure/sovereignty/sovereign-cloud-architecture.json #> #Requires -Version 5.1 #Requires -Modules Az.Accounts, Az.Resources, Az.Policy, Az.ResourceGraph [CmdletBinding()] param( [Parameter(HelpMessage = "Monitor current architecture compliance")] [switch]$Monitoring, [Parameter(HelpMessage = "Apply recommended architecture configuration")] [switch]$Remediation, [Parameter(HelpMessage = "Show what would happen without making changes")] [switch]$WhatIf, [Parameter(HelpMessage = "Enable debug mode with synthetic test data")] [switch]$DebugMode ) $ErrorActionPreference = 'Stop' $PolicyName = "Sovereign Cloud Architectuur - Azure" function Get-AllowedRegions { <# .SYNOPSIS Geeft de lijst met geaccepteerde EU-regio's voor sovereign cloud terug #> [CmdletBinding()] param() return @( "westeurope", "northeurope", "germanywestcentral", "germanynorth", "norwayeast", "norwaywest", "swedencentral", "swedensouth", "uksouth", "ukwest", "francecentral", "francesouth", "switzerlandnorth", "switzerlandwest", "italynorth", "spaincentral", "polandcentral" ) } function Connect-RequiredServices { [CmdletBinding()] param( [switch]$DebugMode ) if ($DebugMode) { Write-Verbose "DebugMode is ingeschakeld: er wordt geen verbinding met Azure gemaakt." return } if (-not (Get-AzContext -ErrorAction SilentlyContinue)) { Connect-AzAccount -ErrorAction Stop | Out-Null } } function Test-SovereignCloudArchitecture { <# .SYNOPSIS Analyseert de Azure-architectuur op compliance met sovereign cloud principes .OUTPUTS PSCustomObject met architectuuranalyse en compliance-status #> [CmdletBinding()] param( [switch]$DebugMode ) $allowedRegions = Get-AllowedRegions if ($DebugMode) { # Synthetische testdata voor lokale validatie zonder cloudverbinding return [PSCustomObject]@{ Mode = "Debug" ManagementGroupsConfigured = $true ManagementGroupsCount = 5 SubscriptionsCount = 12 TotalResources = 450 ResourcesInAllowedRegions = 420 ResourcesOutsideAllowedRegions = 30 CompliancePercentage = [math]::Round((420 / 450) * 100, 1) PoliciesConfigured = $true PoliciesCount = 8 ResourceLocksConfigured = $true LocksCount = 65 LandingZonesConfigured = $true LandingZonesCount = 4 NetworkIsolationConfigured = $true PrivateEndpointsCount = 28 IsCompliant = $false DetectedRegions = @("westeurope", "northeurope", "eastus", "westus") ArchitectureScore = 78 } } # Haal management groups op $managementGroups = @() try { $managementGroups = Get-AzManagementGroup -ErrorAction SilentlyContinue } catch { Write-Verbose "Kon management groups niet ophalen: $_" } # Controleer Azure Policies voor soevereiniteit $policiesConfigured = $false $policiesCount = 0 try { $sovereigntyPolicies = Get-AzPolicyDefinition -ErrorAction SilentlyContinue | Where-Object { $_.Properties.DisplayName -like "*allowed locations*" -or $_.Properties.DisplayName -like "*allowed regions*" -or $_.Properties.DisplayName -like "*data residency*" -or $_.Properties.DisplayName -like "*sovereignty*" -or $_.Properties.DisplayName -like "*encryption*" } if ($sovereigntyPolicies) { $policiesConfigured = $true $policiesCount = $sovereigntyPolicies.Count } } catch { Write-Verbose "Kon policies niet ophalen: $_" } # Haal subscriptions en resources op $subscriptions = Get-AzSubscription -ErrorAction Stop | Where-Object { $_.State -eq 'Enabled' } $totalResources = 0 $resourcesInAllowedRegions = 0 $resourcesOutsideAllowedRegions = 0 $regions = [System.Collections.Generic.HashSet[string]]::new([System.StringComparer]::OrdinalIgnoreCase) $locksCount = 0 $privateEndpointsCount = 0 foreach ($sub in $subscriptions) { Set-AzContext -SubscriptionId $sub.Id -ErrorAction Stop | Out-Null try { # Controleer resource locks $locks = Get-AzResourceLock -ErrorAction SilentlyContinue $locksCount += $locks.Count # Haal resources op via Resource Graph voor betere prestaties try { $resources = Search-AzGraph -Query "Resources | where type != 'microsoft.azureactivedirectory/b2ctenants' | project name, type, location, resourceGroup" -Subscription $sub.Id -ErrorAction SilentlyContinue if ($resources) { foreach ($r in $resources) { if (-not $r.location) { continue } $totalResources++ $null = $regions.Add($r.location.ToLowerInvariant()) if ($allowedRegions -contains $r.location.ToLowerInvariant()) { $resourcesInAllowedRegions++ } else { $resourcesOutsideAllowedRegions++ } } } # Controleer private endpoints $privateEndpoints = Search-AzGraph -Query "Resources | where type == 'microsoft.network/privateendpoints' | project name" -Subscription $sub.Id -ErrorAction SilentlyContinue if ($privateEndpoints) { $privateEndpointsCount += $privateEndpoints.Count } } catch { # Fallback naar Get-AzResource als Resource Graph niet beschikbaar is Write-Verbose "Resource Graph niet beschikbaar, gebruik Get-AzResource: $_" $resources = Get-AzResource -ErrorAction SilentlyContinue if ($resources) { foreach ($r in $resources) { if (-not $r.Location) { continue } $totalResources++ $null = $regions.Add($r.Location.ToLowerInvariant()) if ($allowedRegions -contains $r.Location.ToLowerInvariant()) { $resourcesInAllowedRegions++ } else { $resourcesOutsideAllowedRegions++ } } } } } catch { Write-Verbose "Kon resources voor subscription '$($sub.Name)' niet ophalen: $_" } } $compliancePercentage = $null if ($totalResources -gt 0) { $compliancePercentage = [math]::Round(($resourcesInAllowedRegions / $totalResources) * 100, 1) } # Controleer landing zones (indicatie op basis van naming conventions en structuur) $landingZonesConfigured = $false $landingZonesCount = 0 try { $resourceGroups = Get-AzResourceGroup -ErrorAction SilentlyContinue $landingZonePatterns = @("*landing*", "*lz*", "*platform*", "*hub*") foreach ($rg in $resourceGroups) { foreach ($pattern in $landingZonePatterns) { if ($rg.ResourceGroupName -like $pattern) { $landingZonesCount++ $landingZonesConfigured = $true break } } } } catch { Write-Verbose "Kon landing zones niet controleren: $_" } # Controleer netwerkisolatie (indicatie op basis van private endpoints) $networkIsolationConfigured = ($privateEndpointsCount -gt 0) # Bereken architectuurscore $architectureScore = 0 if ($managementGroups.Count -gt 0) { $architectureScore += 15 } if ($policiesConfigured) { $architectureScore += 20 } if ($compliancePercentage -ge 95) { $architectureScore += 25 } elseif ($compliancePercentage -ge 80) { $architectureScore += 15 } elseif ($compliancePercentage -ge 50) { $architectureScore += 5 } if ($locksCount -gt 0) { $architectureScore += 10 } if ($landingZonesConfigured) { $architectureScore += 15 } if ($networkIsolationConfigured) { $architectureScore += 15 } $isCompliant = ($policiesConfigured -and $resourcesOutsideAllowedRegions -eq 0 -and $landingZonesConfigured -and $networkIsolationConfigured) [PSCustomObject]@{ Mode = "Live" ManagementGroupsConfigured = ($managementGroups.Count -gt 0) ManagementGroupsCount = $managementGroups.Count SubscriptionsCount = $subscriptions.Count TotalResources = $totalResources ResourcesInAllowedRegions = $resourcesInAllowedRegions ResourcesOutsideAllowedRegions = $resourcesOutsideAllowedRegions CompliancePercentage = $compliancePercentage PoliciesConfigured = $policiesConfigured PoliciesCount = $policiesCount ResourceLocksConfigured = ($locksCount -gt 0) LocksCount = $locksCount LandingZonesConfigured = $landingZonesConfigured LandingZonesCount = $landingZonesCount NetworkIsolationConfigured = $networkIsolationConfigured PrivateEndpointsCount = $privateEndpointsCount IsCompliant = $isCompliant DetectedRegions = @($regions) | Sort-Object ArchitectureScore = $architectureScore } } function Test-Compliance { <# .SYNOPSIS Wrapper function die compliance-status test .OUTPUTS Returns monitoring result object with isCompliant property #> [CmdletBinding()] param( [switch]$DebugMode ) $result = Test-SovereignCloudArchitecture -DebugMode:$DebugMode return [PSCustomObject]@{ isCompliant = $result.IsCompliant details = $result } } function Invoke-Monitoring { <# .SYNOPSIS Monitors and reports current sovereign cloud architecture compliance .DESCRIPTION Checks current architecture against sovereign cloud principles. Reports compliance status and identifies areas for improvement. .OUTPUTS Returns hashtable with: - isCompliant: Boolean indicating overall compliance - details: Detailed findings #> [CmdletBinding()] param( [switch]$DebugMode ) try { Write-Host "`nMonitoring:" -ForegroundColor Yellow Connect-RequiredServices -DebugMode:$DebugMode Write-Host "Analyseren van sovereign cloud architectuur..." -ForegroundColor Gray $result = Test-SovereignCloudArchitecture -DebugMode:$DebugMode Write-Host "" -ForegroundColor White Write-Host "========================================" -ForegroundColor Cyan Write-Host $PolicyName -ForegroundColor Cyan Write-Host "========================================" -ForegroundColor Cyan Write-Host ("Modus : {0}" -f $result.Mode) -ForegroundColor White Write-Host ("Management Groups geconfigureerd: {0}" -f $(if ($result.ManagementGroupsConfigured) { "Ja ($($result.ManagementGroupsCount))" } else { "Nee" })) -ForegroundColor $(if ($result.ManagementGroupsConfigured) { 'Green' } else { 'Yellow' }) Write-Host ("Subscripties : {0}" -f $result.SubscriptionsCount) -ForegroundColor White Write-Host ("Totaal aantal resources : {0}" -f $result.TotalResources) -ForegroundColor White Write-Host ("Resources in toegestane regio's: {0}" -f $result.ResourcesInAllowedRegions) -ForegroundColor White Write-Host ("Resources buiten toegestane regio's: {0}" -f $result.ResourcesOutsideAllowedRegions) -ForegroundColor $(if ($result.ResourcesOutsideAllowedRegions -eq 0) { 'Green' } else { 'Yellow' }) if ($null -ne $result.CompliancePercentage) { Write-Host ("Compliance percentage : {0}%" -f $result.CompliancePercentage) -ForegroundColor $(if ($result.CompliancePercentage -ge 95) { 'Green' } elseif ($result.CompliancePercentage -ge 80) { 'Yellow' } else { 'Red' }) } else { Write-Host "Compliance percentage : n.v.t. (geen resources gevonden)" -ForegroundColor Yellow } Write-Host ("Policies geconfigureerd : {0}" -f $(if ($result.PoliciesConfigured) { "Ja ($($result.PoliciesCount))" } else { "Nee" })) -ForegroundColor $(if ($result.PoliciesConfigured) { 'Green' } else { 'Yellow' }) Write-Host ("Resource locks geconfigureerd : {0}" -f $(if ($result.ResourceLocksConfigured) { "Ja ($($result.LocksCount) locks)" } else { "Nee" })) -ForegroundColor $(if ($result.ResourceLocksConfigured) { 'Green' } else { 'Yellow' }) Write-Host ("Landing zones geconfigureerd : {0}" -f $(if ($result.LandingZonesConfigured) { "Ja ($($result.LandingZonesCount))" } else { "Nee" })) -ForegroundColor $(if ($result.LandingZonesConfigured) { 'Green' } else { 'Yellow' }) Write-Host ("Netwerkisolatie geconfigureerd : {0}" -f $(if ($result.NetworkIsolationConfigured) { "Ja ($($result.PrivateEndpointsCount) private endpoints)" } else { "Nee" })) -ForegroundColor $(if ($result.NetworkIsolationConfigured) { 'Green' } else { 'Yellow' }) Write-Host ("Architectuurscore : {0}/100" -f $result.ArchitectureScore) -ForegroundColor $(if ($result.ArchitectureScore -ge 80) { 'Green' } elseif ($result.ArchitectureScore -ge 60) { 'Yellow' } else { 'Red' }) if ($result.DetectedRegions -and $result.DetectedRegions.Count -gt 0) { Write-Host ("Gedetecteerde regio's : {0}" -f ($result.DetectedRegions -join ", ")) -ForegroundColor White } Write-Host "" -ForegroundColor White Write-Host "========================================" -ForegroundColor Cyan Write-Host "SUMMARY:" -ForegroundColor Cyan if ($result.IsCompliant) { Write-Host "`n[OK] COMPLIANT" -ForegroundColor Green Write-Host "De Azure-architectuur voldoet aan sovereign cloud principes." -ForegroundColor Green } else { Write-Host "`n[FAIL] NON-COMPLIANT" -ForegroundColor Red if (-not $result.ManagementGroupsConfigured) { Write-Host " - Management group-hiƫrarchie is niet geconfigureerd" -ForegroundColor Yellow } if (-not $result.PoliciesConfigured) { Write-Host " - Azure Policies voor soevereiniteit zijn niet geconfigureerd" -ForegroundColor Yellow } if ($result.ResourcesOutsideAllowedRegions -gt 0) { Write-Host " - Er zijn $($result.ResourcesOutsideAllowedRegions) resources buiten toegestane regio's" -ForegroundColor Yellow } if (-not $result.ResourceLocksConfigured) { Write-Host " - Resource locks zijn niet geconfigureerd voor kritieke workloads" -ForegroundColor Yellow } if (-not $result.LandingZonesConfigured) { Write-Host " - Landing zones zijn niet geconfigureerd" -ForegroundColor Yellow } if (-not $result.NetworkIsolationConfigured) { Write-Host " - Netwerkisolatie via private endpoints is niet geconfigureerd" -ForegroundColor Yellow } } return @{ isCompliant = $result.IsCompliant details = $result timestamp = Get-Date } } catch { Write-Host "`n[FAIL] ERROR during monitoring: $_" -ForegroundColor Red throw } } function Invoke-Remediation { <# .SYNOPSIS Applies recommended sovereign cloud architecture configuration .DESCRIPTION Implements recommended configuration to meet sovereign cloud architecture principles. Uses native PowerShell cmdlets where possible. .PARAMETER WhatIf Shows what would be changed without making actual changes #> [CmdletBinding(SupportsShouldProcess)] param( [switch]$WhatIf, [switch]$DebugMode ) try { Write-Host "`nRemediation:" -ForegroundColor Yellow if ($DebugMode) { Write-Host "[INFO] DebugMode: geen daadwerkelijke wijzigingen worden uitgevoerd" -ForegroundColor Yellow return } Connect-RequiredServices Write-Host "Toepassen van sovereign cloud architectuurconfiguratie..." -ForegroundColor Gray # Controleer eerst de huidige status $currentStatus = Test-SovereignCloudArchitecture if ($currentStatus.IsCompliant) { Write-Host " [OK] Sovereign cloud architectuur is al correct geconfigureerd" -ForegroundColor Green return } # Configureer management group-hiƫrarchie indien nodig if (-not $currentStatus.ManagementGroupsConfigured) { Write-Host "`n[INFO] Management group-hiƫrarchie configureren:" -ForegroundColor Yellow Write-Host " Overweeg de volgende stappen:" -ForegroundColor White Write-Host " 1. Ontwerp een hiƫrarchie met root management group voor centrale policies" -ForegroundColor White Write-Host " 2. Maak management groups per dataclassificatie of compliance-eis" -ForegroundColor White Write-Host " 3. Wijs Azure Policies toe op management group-niveau" -ForegroundColor White Write-Host " 4. Documenteer de hiƫrarchie in architectuurdocumentatie" -ForegroundColor White if ($PSCmdlet.ShouldProcess("Management Groups", "Configure hierarchy")) { Write-Host " [NOTE] Management group-configuratie vereist handmatige stappen in Azure Portal of via Infrastructure as Code" -ForegroundColor Yellow } } # Configureer Azure Policies indien nodig if (-not $currentStatus.PoliciesConfigured) { Write-Host "`n[INFO] Azure Policies voor soevereiniteit configureren:" -ForegroundColor Yellow Write-Host " Overweeg de volgende policies:" -ForegroundColor White Write-Host " 1. Allowed locations policy voor regionale restricties" -ForegroundColor White Write-Host " 2. Encryption policies voor data-at-rest" -ForegroundColor White Write-Host " 3. Network security policies voor isolatie" -ForegroundColor White Write-Host " 4. Resource locks policies voor kritieke workloads" -ForegroundColor White if ($PSCmdlet.ShouldProcess("Azure Policies", "Configure sovereignty policies")) { Write-Host " [NOTE] Policy-configuratie vereist handmatige stappen in Azure Portal" -ForegroundColor Yellow } } # Geef aanbevelingen voor resources buiten toegestane regio's if ($currentStatus.ResourcesOutsideAllowedRegions -gt 0) { Write-Host "`n[INFO] Resources buiten toegestane regio's gevonden:" -ForegroundColor Yellow Write-Host " Aantal resources: $($currentStatus.ResourcesOutsideAllowedRegions)" -ForegroundColor White Write-Host " Overweeg de volgende acties:" -ForegroundColor White Write-Host " 1. Identificeer welke resources buiten toegestane regio's draaien" -ForegroundColor White Write-Host " 2. Evalueer of migratie naar toegestane regio's mogelijk is" -ForegroundColor White Write-Host " 3. Documenteer uitzonderingen indien migratie niet mogelijk is" -ForegroundColor White Write-Host " 4. Plan migraties binnen reguliere changeprocessen" -ForegroundColor White } # Configureer landing zones indien nodig if (-not $currentStatus.LandingZonesConfigured) { Write-Host "`n[INFO] Landing zones configureren:" -ForegroundColor Yellow Write-Host " Overweeg de volgende stappen:" -ForegroundColor White Write-Host " 1. Ontwerp standaard landing zones met soevereiniteitsprincipes" -ForegroundColor White Write-Host " 2. Implementeer landing zones via Infrastructure as Code" -ForegroundColor White Write-Host " 3. Configureer automatische compliance en beveiliging" -ForegroundColor White Write-Host " 4. Documenteer landing zones in architectuurdocumentatie" -ForegroundColor White if ($PSCmdlet.ShouldProcess("Landing Zones", "Configure standard landing zones")) { Write-Host " [NOTE] Landing zone-configuratie vereist Infrastructure as Code (Bicep/Terraform)" -ForegroundColor Yellow } } # Configureer netwerkisolatie indien nodig if (-not $currentStatus.NetworkIsolationConfigured) { Write-Host "`n[INFO] Netwerkisolatie configureren:" -ForegroundColor Yellow Write-Host " Overweeg de volgende stappen:" -ForegroundColor White Write-Host " 1. Implementeer private endpoints voor PaaS-diensten" -ForegroundColor White Write-Host " 2. Configureer hub-and-spoke-topologie voor centrale netwerkdiensten" -ForegroundColor White Write-Host " 3. Implementeer Network Security Groups voor granular toegangscontrole" -ForegroundColor White Write-Host " 4. Documenteer netwerkarchitectuur in architectuurdocumentatie" -ForegroundColor White if ($PSCmdlet.ShouldProcess("Network Isolation", "Configure private endpoints and network isolation")) { Write-Host " [NOTE] Netwerkisolatie vereist netwerkarchitectuurplanning en implementatie" -ForegroundColor Yellow } } Write-Host "`n[OK] Remediation-aanbevelingen gepresenteerd" -ForegroundColor Green Write-Host " Voer de bovenstaande stappen uit om sovereign cloud architectuur volledig te implementeren" -ForegroundColor White } catch { Write-Host "`n[FAIL] ERROR during remediation: $_" -ForegroundColor Red throw } } function Invoke-Implementation { <# .SYNOPSIS Implementeert configuratie (delegeert naar remediatie) #> [CmdletBinding()] param( [switch]$WhatIf, [switch]$DebugMode ) Invoke-Remediation -WhatIf:$WhatIf -DebugMode:$DebugMode } # ============================================================================ # MAIN EXECUTION # ============================================================================ try { # Determine which action to perform if ($Remediation) { if ($WhatIf) { Write-Host "WhatIf: Would apply remediation" -ForegroundColor Yellow Invoke-Remediation -WhatIf -DebugMode:$DebugMode } else { Invoke-Remediation -DebugMode:$DebugMode } } elseif ($Monitoring) { $result = Invoke-Monitoring -DebugMode:$DebugMode # Exit with appropriate code for automation if ($result.isCompliant) { exit 0 # Success - Compliant } else { exit 1 # Warning - Non-compliant } } else { # No parameters - show usage Write-Host "Available parameters:" -ForegroundColor Yellow Write-Host " -Monitoring : Check current architecture compliance" -ForegroundColor Gray Write-Host " -Remediation : Apply recommended architecture configuration" -ForegroundColor Gray Write-Host " -WhatIf : Preview changes without applying" -ForegroundColor Gray Write-Host " -DebugMode : Use synthetic test data (no Azure connection)" -ForegroundColor Gray Write-Host "`nExample: .\sovereign-cloud-architecture.ps1 -Monitoring" -ForegroundColor Cyan Write-Host "Example: .\sovereign-cloud-architecture.ps1 -Monitoring -DebugMode" -ForegroundColor Cyan } } catch { Write-Error "Script execution failed: $_" exit 2 # Error } finally { Write-Host "`n========================================`n" -ForegroundColor Cyan } # ============================================================================ # EXIT CODES # ============================================================================ # 0 = Success / Compliant # 1 = Warning / Non-compliant # 2 = Error / Execution failed

Risico zonder implementatie

Risico zonder implementatie
High: Zonder een expliciet ontworpen sovereign cloud architectuur ontstaat er een risico dat Azure-omgevingen organisch groeien zonder duidelijke focus op digitale soevereiniteit. Dit kan leiden tot verlies van strategische controle, blootstelling aan extraterritoriale bevoegdheden, afhankelijkheid van niet-EU jurisdicties en kritieke bevindingen bij audits. Voor kritieke infrastructuur kan dit leiden tot operationele risico's en vragen van toezichthouders over de mate van controle en onafhankelijkheid.

Management Samenvatting

Een sovereign cloud architectuur vormt de technische en organisatorische basis voor het realiseren van digitale soevereiniteit binnen Azure. Door architectuurprincipes vast te leggen, management group-hiƫrarchieƫn te ontwerpen, landing zones te implementeren en periodieke architectuuranalyses uit te voeren met een PowerShell-script, ontstaat aantoonbare controle over cloudomgevingen en soevereiniteitsnaleving. Dit artikel geeft cloudarchitecten, CISO's en strategische adviseurs een concreet raamwerk om een sovereign cloud architectuur integraal te verankeren in cloudstrategie, risicobeheersing en governance.