Get-RedirectURIs.ps1

Function Get-RedirectURIs {
    [CmdletBinding()]
    param (
        $AppObjectID
    )
    $t1 = @'
 
        Designed and managed by
              ___ _
             / _ \ (_)
            / /_\ \ __ _ _ __ ___ _ __ ___ _ _ __
            | _ |/ _` | '_ ` _ \| '_ ` _ \| | '__|
            | | | | (_| | | | | | | | | | | | | |
            \_| |_/\__,_|_| |_| |_|_| |_| |_|_|_|
 
            Contact : aammir.mirza@hotmail.com
 
'@

    Write-Verbose "$($t1)"
    # Constructing MS Graph Authentication header
    $azContext = Get-AzContext
    $token = Get-AzAccessToken -ResourceTypeName MSGraph
    $headers = @{
        'Content-Type'  = 'application/json'
        'Authorization' = 'Bearer ' + $token.Token
    }
    if ($AppObjectID) {
        $APIResponse = Invoke-RestMethod "https://graph.microsoft.com/v1.0/applications/$($AppObjectID)" -Method 'GET' -Headers $headers
        $Array = @();
        $redirects = $APIResponse | Where-Object { $_.web.redirectUris -match 'ondemand.com' }
        Write-Verbose "App Registration - $($redirects.displayName)"
        foreach ($parsed in $redirects) {
            try {
                foreach ($testUri in $redirects.web.redirectUris) {
                    $toPing = ($testUri -split 'https://' -split '/')[1]
                    if ($toPing) {
                        Write-Verbose " Pinging $($toPing)"
                        $s = Resolve-Dns $toPing;
                        if ($s.HasError) {
                            $owner = "https://graph.microsoft.com/v1.0/myorganization/applications/$($redirects.Id)/owners"
                            $response2 = Invoke-RestMethod $owner -Method 'GET' -Headers $headers
                            $owners = ($response2.value.userPrincipalName -join '; ')
                            $Array += [PSCustomObject]@{
                                'SPN_Name'            = $($redirects.displayName)
                                'App'                 = $testUri
                                'Owners'              = $owners
                                'passwordCredentials' = $($redirects.displayName.passwordCredentials.endDateTime)
                            }
                            Write-Verbose " Subdomain takeover possible for [$($parsed.displayName) | $($testUri)] | [$($redirects.displayName)] | [$owners]" -ForegroundColor Red
                    ('-' * 75)
                        }
                    }
                }
            }
            catch {
                $owner = "https://graph.microsoft.com/v1.0/myorganization/applications/$($currentItemName.Id)/owners"
                $response2 = Invoke-RestMethod $owner -Method 'GET' -Headers $headers
                $owners = ($response2.value.userPrincipalName -join '; ')
                $Array += [PSCustomObject]@{
                    'SPN_Name'            = $($redirects.displayName)
                    'App'                 = $testUri
                    'Owners'              = $owners
                    'passwordCredentials' = $($redirects.displayName.passwordCredentials.endDateTime)
                }
                Write-Verbose "Subdomain takeover possible for [$($testUri)] | [$($redirects.displayName)] | [$owners]" -ForegroundColor red
        ('-' * 75)
            }
        }
        $Array
    }
    else {
        Write-Verbose 'Running for whole tenant for all App Registrations.'
        $APIResponse = Invoke-RestMethod 'https://graph.microsoft.com/v1.0/applications' -Method 'GET' -Headers $headers
        $CloudAppRegistration = $APIResponse.Value
        $UserNextLink = $APIResponse.'@odata.nextLink'
        while ($UserNextLink -ne $null) {
            $APIResponse = (Invoke-RestMethod -Headers $headers -Uri $UserNextLink -Method Get)
            $UserNextLink = $APIResponse.'@odata.nextLink'
            $CloudAppRegistration += $APIResponse.value
        }
        $CloudAppRegistration.Count

        # $CloudAppRegistration | Format-Table DisplayName -AutoSize
        # $response | ConvertTo-Json

        $Url = "https://graph.microsoft.com/v1.0/applications?$select=displayName"
        #$headers = @{Authorization = "Bearer $($Tokenresponse.access_token)"}
        $CloudUser = @()
        do {
            $UserResponse = Invoke-RestMethod -Headers $headers -Uri $Url -Method Get
            $CloudUser += $UserResponse.Value
            $Url = $UserResponse.'@odata.nextLink'
        } while ($Url)
        $Array = @();
        foreach ($currentItemName in $CloudUser) {
            $redirects = $currentItemName | Where-Object { $_.web.redirectUris -match 'azurewebsites.net' }
            foreach ($parsed in $redirects) {
                try {
                    foreach ($testUri in $redirects.web.redirectUris) {
                        $toPing = ($testUri -split 'https://' -split '/')[1]
                        if ($toPing) {
                            Write-Verbose " Pinging $($toPing)"
                            $s = Resolve-Dns $toPing;
                            if ($s.HasError) {
                                $owner = "https://graph.microsoft.com/v1.0/myorganization/applications/$($currentItemName.Id)/owners"
                                $response2 = Invoke-RestMethod $owner -Method 'GET' -Headers $headers
                                $owners = ($response2.value.userPrincipalName -join '; ')
                                $Array += [PSCustomObject]@{
                                    'SPN_Name'            = $($redirects.displayName)
                                    'App'                 = $testUri
                                    'Owners'              = $owners
                                    'passwordCredentials' = $($redirects.displayName.passwordCredentials.endDateTime)
                                }
                                Write-Verbose " Subdomain takeover possible for [$($parsed.displayName) | $($testUri)] | [$($redirects.displayName)] | [$owners]" -ForegroundColor Red
                        ('-' * 75)
                            }
                        }
                    }
                }
                catch {
                    $owner = "https://graph.microsoft.com/v1.0/myorganization/applications/$($currentItemName.Id)/owners"
                    $response2 = Invoke-RestMethod $owner -Method 'GET' -Headers $headers
                    $owners = ($response2.value.userPrincipalName -join '; ')
                    $Array += [PSCustomObject]@{
                        'SPN_Name'            = $($redirects.displayName)
                        'App'                 = $testUri
                        'Owners'              = $owners
                        'passwordCredentials' = $($redirects.displayName.passwordCredentials.endDateTime)
                    }
                    Write-Verbose "Subdomain takeover possible for [$($testUri)] | [$($redirects.displayName)] | [$owners]" -ForegroundColor red
            ('-' * 75)
                }
            }
        }
        $Array | Format-Table
        $dates = (Get-Date).tostring('yyyyMMdd')
        $Array | Export-Csv -Path ".\subdomain_takeover_$($dates).csv" -NoTypeInformation -Append
    }
}