Workloads/Get-AzureData.ps1

# Get-AzureData.ps1
# Collects Azure subscription presence for scoping awareness.
# Full Azure migration is out of scope -- this is a signal only.
# Part of the M365-QuickAssess module -- not exported.

function Get-AzureData
{
    param
    (
        $Assessment
    )

    Write-Log "Collecting Azure subscription data"

    # -------------------------------------------------------------------
    # Connect to Azure
    # -------------------------------------------------------------------
    try
    {
        Connect-AzureService
    }
    catch
    {
        Write-Log "Azure connection failed -- skipping Azure collection" "WARN"

        $Assessment.Azure.HasAzureSubscriptions  = $false
        $Assessment.Azure.AzureSubscriptionCount = 0
        $Assessment.Azure.HasSubscriptionAccess  = $false
        return
    }

    # -------------------------------------------------------------------
    # Get Subscriptions
    # -------------------------------------------------------------------
    $subs        = @()
    $accessDenied = $false

    try
    {
        $subs = Get-AzSubscription -TenantId $script:Context.TenantId -ErrorAction Stop
    }
    catch
    {
        if ( $_.Exception.Message -match "AuthorizationFailed|Forbidden|403" )
        {
            Write-Log "No access to Azure subscriptions (RBAC)" "WARN"
            $accessDenied = $true
        }
        else
        {
            Write-Log "Failed to retrieve Azure subscriptions: $( $_.Exception.Message )" "WARN"
        }
    }

    # -------------------------------------------------------------------
    # Filter out AAD-only placeholder and non-enabled subscriptions
    # QuotaId AAD_2015-09-01 is the reliable identifier for the
    # default AAD placeholder that exists in every tenant.
    # -------------------------------------------------------------------
    $realSubs = $subs | Where-Object {
        $_.Id -and
        $_.Id -ne "N/A" -and
        $_.State -eq "Enabled" -and
        $_.Name -notmatch "Access to Azure Active Directory" -and
        $_.SubscriptionPolicies.QuotaId -notmatch "AAD_2015-09-01|MSDN_2014-05-01"
    }

    $count = ( $realSubs | Measure-Object ).Count

    Write-Log "Azure subscriptions found: $count (raw: $( $subs.Count ))"

    # -------------------------------------------------------------------
    # Populate Schema
    # -------------------------------------------------------------------
    $Assessment.Azure.HasAzureSubscriptions  = ( $count -gt 0 )
    $Assessment.Azure.AzureSubscriptionCount = $count
    $Assessment.Azure.HasSubscriptionAccess  = ( -not $accessDenied )

    # -------------------------------------------------------------------
    # Findings
    # -------------------------------------------------------------------
    if ( $accessDenied )
    {
        $Assessment.Findings += New-Finding `
            -Type           "AzureAccessDenied" `
            -Summary        "Azure subscriptions may exist but access was denied" `
            -Category       "Azure" `
            -Severity       "Info" `
            -Impact         "Unable to confirm Azure subscription presence due to insufficient RBAC permissions." `
            -Recommendation "Ask the customer to confirm whether Azure subscriptions are in use in this tenant."
    }
    elseif ( $count -eq 0 )
    {
        $Assessment.Findings += New-Finding `
            -Type           "NoAzureSubscriptions" `
            -Summary        "No Azure subscriptions detected" `
            -Category       "Azure" `
            -Severity       "Info" `
            -Impact         "No Azure subscriptions found in this tenant." `
            -Recommendation "Confirm with the customer that Azure is not in use before proceeding."
    }
    else
    {
        $subDetails = $realSubs | ForEach-Object { "$( $_.Name ) - $( $_.Id )" }

        $Assessment.Findings += New-Finding `
            -Type           "AzureSubscriptionsDetected" `
            -Summary        "$count Azure subscription(s) detected" `
            -Category       "Azure" `
            -Severity       "Info" `
            -Details        $subDetails `
            -Impact         "Azure resources are tied to this tenant and are outside the scope of an M365 migration." `
            -Recommendation "Engage the customer on Azure workloads separately. Confirm which subscriptions need to move and plan accordingly."
    }
}