Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Gather Host Pools Function #2

Open
L1mbusFr1ng3 opened this issue Oct 29, 2023 · 15 comments
Open

Gather Host Pools Function #2

L1mbusFr1ng3 opened this issue Oct 29, 2023 · 15 comments

Comments

@L1mbusFr1ng3
Copy link

I get the following error and I have the variables correctly set. Please help. I really want to use this code then implement for a big client.

The property 'text' cannot be found on this object. Verify that the property exists and can be set.
At C:\Users\ericd\Downloads\New Script\AVD Shadowing.ps1:243 char:5

  • $Subscriptions.text          = $AVDSubscriptions
    
  • ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    
    • CategoryInfo : InvalidOperation: (:) [], RuntimeException
    • FullyQualifiedErrorId : PropertyNotFound

Gather_HostPools : The term 'Gather_HostPools' is not recognized as the name of a cmdlet, function, script file, or
operable program. Check the spelling of the name, or if a path was included, verify that the path is correct and try
again.
At C:\Users\ericd\Downloads\New Script\AVD Shadowing.ps1:245 char:5

  • Gather_HostPools
    
  • ~~~~~~~~~~~~~~~~
    
    • CategoryInfo : ObjectNotFound: (Gather_HostPools:String) [], CommandNotFoundException
    • FullyQualifiedErrorId : CommandNotFoundException
@GarryDown
Copy link
Owner

Please can you check you have the variable set up correctly, with the quotes and if you have two subscriptions to check they are separated by a comma

Single Subscription
$AVDSubscriptions = @('11111111-1111-1111-1111-111111111111')

Multiple Subscriptions
$AVDSubscriptions = @('11111111-1111-1111-1111-111111111111', '22222222-2222-2222-2222-222222222222', '33333333-3333-3333-3333-333333333333')

Being unable to read the text value would suggest it is not getting the AVDSubscriptions value it expected

@L1mbusFr1ng3
Copy link
Author

So I put the correct Subscription ID.
I went to Subscriptions in Azure and copied the Subscription ID.
What else could this be? I really need to get this working for a work project that is way behind. Any help you can provide would be greatly appreciated.

@L1mbusFr1ng3
Copy link
Author

This sample code works fine to list user sessions and host pool. I can't reconcile getting the host name of each associated user. So I'd like to use your awesome code. This code works to get one of my host pools user sessions. Would this help in troubleshooting getting your code to work? I'm in SPRING edition.

Even if I can just define one host pool that would help me. Please help.

Add-Type -AssemblyName PresentationFramework

Install required module if not already installed

Install-Module -Name Az.DesktopVirtualization

Connect to Azure account

Connect-AzAccount

Set the context to the appropriate subscription

Set-AzContext -SubscriptionId "53522dc9-55fa-48fa-a0e7-73d261d61f71"

Set the target resource group

$resourceGroupName = "RG-AVD"

Create a simple WPF form

$window = New-Object System.Windows.Window
$window.Title = "AVD User Sessions"
$window.Width = 800
$window.Height = 600

Create a ListView

$listView = New-Object System.Windows.Controls.ListView
$listView.View = (New-Object System.Windows.Controls.GridView)

Create columns for the ListView

$listView.View.Columns.Add((New-Object System.Windows.Controls.GridViewColumn -Property @{Header = "User Session"; Width = 200; DisplayMemberBinding = New-Object System.Windows.Data.Binding 'UserPrincipalName'}))
$listView.View.Columns.Add((New-Object System.Windows.Controls.GridViewColumn -Property @{Header = "Host Pool"; Width = 200; DisplayMemberBinding = New-Object System.Windows.Data.Binding 'HostPoolName'}))
$listView.View.Columns.Add((New-Object System.Windows.Controls.GridViewColumn -Property @{Header = "Host Name"; Width = 200; DisplayMemberBinding = New-Object System.Windows.Data.Binding 'HostName'}))

Get all AVD host pools in the specified resource group

$avdHostPools = Get-AzWvdHostPool -ResourceGroupName $resourceGroupName

Create an empty list to store the data

$dataList = New-Object System.Collections.Generic.List[Object]

Collect the user session data

if ($avdHostPools -ne $null) {
foreach ($avdHostPool in $avdHostPools) {

    # Get user sessions for the current host pool
    $userSessions = Get-AzWvdUserSession -ResourceGroupName $resourceGroupName -HostPoolName $avdHostPool.Name
    if ($userSessions -ne $null) {
        foreach ($session in $userSessions) {
            $dataList.Add([PSCustomObject]@{
                UserPrincipalName = $session.UserPrincipalName
                HostPoolName = $avdHostPool.Name
                HostName = $session.HostName
            })
        }
    }
}

} else {
$window.Close()
Write-Host "No AVD Host Pools found in resource group '$resourceGroupName'."
}

Populate the ListView with data

$dataList | ForEach-Object {
$listView.Items.Add($_)
}

Double-click event handler

$listView.Add_MouseDoubleClick({
$selectedItem = $listView.SelectedItem
if ($selectedItem -ne $null) {
$user = $selectedItem.UserPrincipalName
$hostPool = $selectedItem.HostPoolName
$host = $selectedItem.HostName
[System.Windows.MessageBox]::Show("User: $usernHost Pool: $hostPoolnHost: $host", "Row Double-Clicked")
}
})

$window.Content = $listView

Display the window

$window.ShowDialog() | Out-Null

@GarryDown
Copy link
Owner

I have spotted my error and will provided an updated script as soon as I can

Plus, I unfortunately gave you the wrong info regarding what to set the Azure Subscription value too, its not the Subscription ID its the Subscription name

Single Subscription
$AVDSubscriptions = @('Name_of_my_Only_Subscription')

Multiple Subscriptions
$AVDSubscriptions = @('Name_of_my_first_subscription', 'Name_of_my_second_subscription', 'Name_of_my_third_subscription')

@L1mbusFr1ng3
Copy link
Author

Thank you so much. Can't wait for the modifications! Anxiousyly await. Thank you so much for your time.

@L1mbusFr1ng3
Copy link
Author

If it helps I am now getting this:
10:24:27: ERROR: AVD Subscription Variable not updated

Here is the current code I am using:
<##################################################################################################

Script Name:   AVD Shadowing.ps1
Written By:    Garry Down
Version:       3.0

Change Log: 
-----------
Date         Version      Changes
----         -------      -------
19/06/2020     1.0        Initial Release, supporting Fall Release Only
26/06/2020     1.1        Updated to allow prompt for Authentication if no Service Principal ID
                          Password TXT File Found
06/07/2020     2.0        Updated to allow the Shadowing of both Fall or Spring Release Users
09/07/2020     2.1        Corrected an issue remunerating Active Spring Release Users
29/04/2022     3.0        Support for the Fall Release REMOVED
                          Support for AVD being deployed to more than one Azure Subscriptions


The script has been created to allow an administrator to select a user via a PowerShell GUI and shadow that user


Script works with ONLY with the Spring Releases of AVD


Requirements:
-------------
The Azure AZ PowerShell Modules need to be installed, specific Modules required are:

    Az.Accounts
    Az.DesktopVirtualization


Variables:
----------
    Azure Tenant ID in which the Host Pools reside (Line 78)
    
        AzureTenantId

    The Azure Subscriptions within the Azure Tenant that Host AVD Environments (Line 81)
        
        AVDSubscriptions
        
        Note: This is an array so multiple Resource Groups can be added, seperated by a coma ','
        Examples: 
            @('My Only Subscription')
            @('Subscription One','Subscription Two','Subscription Three')


The Script Actions are:
-----------------------
    Import the required PowerShell Modules

    If the Device running the Shadowing Script has Remote Assistance installed th

    Login into Azure and connect to the configured Azure Tenant ID

    Via the PowerShell GUI:

        If more than One Azure Subscription has been configured Provide a Drop Down Box so the Administrator

        Gather a List of the Host Pools within the Subscription and to populate the Host Pool list

        The required Host Pool is selected

        Populate the User List with all ACTIVE Users connected to the Host Pool

        Select the User to be shadowed

        Enable Remote Control if required

        Shadow the User

##################################################################################################>

Variables \ Arrays

Azure Tenant ID

$AzureTenantId = "f85022b3-aee6-4cd6-a422-37509aec617f"

Subscriptions Hosting AVD Environments

$AVDSubscriptions = @('LAMPS PLUS')

Import Required PowerShell Modules

cls
Write-Host
Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " Importing PowerShell Modules"
$Modules = @('Az')
Foreach ($Module in $Modules) {
if((Get-Module -Name $Module -ErrorAction SilentlyContinue) -eq $false) {
Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " Importing Module" $Module -ForegroundColor DarkYellow
Import-Module -Name $Module -Verbose -ErrorAction SilentlyContinue
}
Else {
Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " PowerShell Module " -NoNewline -ForegroundColor DarkYellow ; Write-Host "'$Module'" -NoNewline -ForegroundColor DarkCyan ; Write-Host " already imported" -ForegroundColor DarkYellow
}
}

Validate Variables

AzureTenantId

If (!($AzureTenantId -match("^({){0,1}[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{12}(}){0,1}$"))) {
Write-Host ; Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " ERROR: " -NoNewline -ForegroundColor Red ; Write-Host "Azure Tenant Id is not a valid GUID"
Break
}

Subscriptions

If ($AVDSubscriptions -eq 'LAMPS PLUS') {
Write-Host ; Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " ERROR: " -NoNewline -ForegroundColor Red ; Write-Host "AVD Subscription Variable not updated"
Break
}

If ($AVDSubscriptions.Count -eq 0) {
Write-Host ; Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " ERROR: " -NoNewline -ForegroundColor Red ; Write-Host "AVD Subscriptions Variable is empty"
Break
}

$WindowPadSubs = 0
If ($AVDSubscriptions.Count -gt 1) {
$WindowPadSubs = 90
}

Check to see if Remote Assistance is installed

$UseMSTSC = $false
$WindowPadMSTSC = 0
If (!(Test-Path -Path 'C:\Windows\System32\msra.exe')) {
Write-Host ; Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " Remote Assistance not Enabled, Switching the Remote Desktop Shadowing"
$UseMSTSC = $true
$WindowPadMSTSC = 50
}

Log into Azure

Write-Host ; Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " Log into Azure"
Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " Prompting for Log In Credentials for Azure Tenant ID " -ForegroundColor DarkYellow -NoNewline ; Write-Host $AzureTenantId -ForegroundColor DarkCyan
$HideOutput = Get-AzContext -ListAvailable | Disconnect-AzAccount
$HideOutput = Connect-AzAccount -Tenant $AzureTenantId -WarningAction SilentlyContinue

Launch Shadow Selector Windows

Write-Host ; Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " Launching Shadow Selector Screen"
Add-Type -AssemblyName System.Windows.Forms
[System.Windows.Forms.Application]::EnableVisualStyles()

$ShadowUser = New-Object system.Windows.Forms.Form
$ShadowUser.ClientSize = New-Object System.Drawing.Size(700,(270 + $WindowPadSubs + $WindowPadMSTSC))
$ShadowUser.text = "User Shadow Selector"
$ShadowUser.TopMost = $false

$Subscriptions_Label = New-Object system.windows.forms.label
$Subscriptions_Label.text = "Select the Azure Subscription the user is connected too"
$Subscriptions_Label.autosize = $true
$Subscriptions_Label.enabled = $false
$Subscriptions_Label.location = New-Object System.Drawing.Point(30,10)
$Subscriptions_Label.Font = 'Microsoft Sans Serif,12'

If ($AVDSubscriptions.Count -gt 1) {
$Subscriptions = New-Object system.Windows.Forms.ComboBox
$Subscriptions.text = ""
$Subscriptions.BackColor = "#c2c2c2"
$Subscriptions.width = 640
$Subscriptions.height = 25
$Subscriptions.location = New-Object System.Drawing.Point(30,45)
$Subscriptions.Font = 'Microsoft Sans Serif,14'

Foreach ($Subs in $AVDSubscriptions) {
    $Subscriptions.Items.Add($Subs) | Out-Null
    }
}

$HostPool_Label = New-Object system.windows.forms.label
$HostPool_Label.text = "Select the Host Pool the user is connected too"
$HostPool_Label.autosize = $true
$HostPool_Label.enabled = $false
$HostPool_Label.location = New-Object System.Drawing.Point(30,(10 + $WindowPadSubs))
$HostPool_Label.Font = 'Microsoft Sans Serif,12'

$HostPool = New-Object system.Windows.Forms.ComboBox
$HostPool.text = "Please Select Subscription to Populate"
$HostPool.BackColor = "#c2c2c2"
$HostPool.width = 640
$HostPool.height = 30
$HostPool.location = New-Object System.Drawing.Point(30,(45 + $WindowPadSubs))
$HostPool.Font = 'Microsoft Sans Serif,14'
$HostPool.enabled = $false

$UserSession_Label = New-Object system.windows.forms.label
$UserSession_Label.text = "Select User to be Shadowed"
$UserSession_Label.autosize = $true
$UserSession_Label.enabled = $false
$UserSession_Label.location = New-Object System.Drawing.Point(30,(100 + $WindowPadSubs))
$UserSession_Label.Font = 'Microsoft Sans Serif,12'

$UserSession = New-Object system.Windows.Forms.ComboBox
$UserSession.text = "Please Select Host Pool to Populate"
$UserSession.width = 640
$UserSession.height = 30
$UserSession.location = New-Object System.Drawing.Point(30,(135 + $WindowPadSubs))
$UserSession.Font = 'Microsoft Sans Serif,14'
$UserSession.enabled = $false

#Hidden Value to calculate Session Host the User is connected too
$UserSessionHost = New-Object system.Windows.Forms.ComboBox
$UserSessionHost.enabled = $false
$UserSessionHost.Visible = $false

#Hidden Value to calculate the Session ID of the Users Session
$UserSessionID = New-Object system.Windows.Forms.ComboBox
$UserSessionID.enabled = $false
$UserSessionID.Visible = $false

$TakeControl = New-Object system.Windows.Forms.CheckBox
$TakeControl.text = " Allow Remote Control of the Users Session"
$TakeControl.width = 600
$TakeControl.height = 30
$TakeControl.location = New-Object System.Drawing.Point(30,(195 + $WindowPadSubs))
$TakeControl.Font = 'Microsoft Sans Serif,12'

$Shadow = New-Object system.Windows.Forms.Button
$Shadow.BackColor = "#f8e71c"
$Shadow.text = "Shadow User"
$Shadow.width = 500
$Shadow.height = 50
$Shadow.enabled = $false
$Shadow.location = New-Object System.Drawing.Point(100,(195 + $WindowPadSubs + $WindowPadMSTSC))
$Shadow.Font = 'Microsoft Sans Serif,14'
$Shadow.ForeColor = "#0000ff"

$ShadowUser.controls.Clear()
$ShadowUser.controls.AddRange(@($HostPool_Label,$HostPool,$UserSession_Label,$UserSession,$Shadow))
If ($AVDSubscriptions.Count -gt 1) {
$ShadowUser.controls.AddRange(@($Subscriptions_Label,$Subscriptions))
}
If ($UseMSTSC -eq $true) {
$ShadowUser.controls.AddRange(@($TakeControl))
}

If ($AVDSubscriptions.Count -gt 1) {
$Subscriptions.Add_SelectedValueChanged({ Gather_HostPools })
}
Else {
$Subscriptions.text = $AVDSubscriptions
$HostPool.text = ""
Gather_HostPools
}

$HostPool.Add_SelectedValueChanged({ HostPoolSelected })

$UserSession.Add_SelectedValueChanged({ $Shadow.enabled = $true })

$Shadow.Add_Click({ ShadowUserSession })

Functions

Function Gather_HostPools {

Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host "   Gathering a list of Host Pools in the Subscription " -ForegroundColor DarkYellow -NoNewLine ; Write-Host $Subscriptions.Text -ForegroundColor DarkCyan

$HostPool.text               = "Gathering a list of Host Pools in the Subscription - Please Wait"
$HostPool.Enabled            = $false

Select-AzSubscription -Subscription $Subscriptions.Text -WarningAction SilentlyContinue | Out-Null

$SubscriptionInfo            = Get-AzSubscription -SubscriptionName $Subscriptions.Text -WarningAction SilentlyContinue
$HostPools                   = Get-AzWvdHostPool -SubscriptionId $SubscriptionInfo.Id -WarningAction SilentlyContinue

$HostPool.Items.Clear()
Foreach ($HP in $HostPools) {
    $HostPool.Items.Add($HP.Name) | Out-Null
    }

$HostPool.text               = "Please Select the Host Pool required"
$HostPool.Enabled            = $true

}

Function HostPoolSelected {

Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host "   Gathering a list of Users Connected to " -ForegroundColor DarkYellow -NoNewLine ; Write-Host $HostPool.Text -ForegroundColor DarkCyan

$SubscriptionInfo            = Get-AzSubscription -SubscriptionName $Subscriptions.Text -WarningAction SilentlyContinue
$HostPoolInfo                = Get-AzWvdHostPool -SubscriptionId $SubscriptionInfo.Id | Where {$_.Name -eq $HostPool.Text}

$UserSession.Items.Clear()
$UserSessionHost.Items.Clear()
$UserSessionID.Items.Clear()

$ActiveUsers                 = Get-AzWvdUserSession -HostPoolName $HostPool.Text -ResourceGroupName $HostPoolInfo.id.Split('/')[4] -ErrorAction SilentlyContinue -Filter "SessionState eq 'active'"

If ($ActiveUsers.Count -eq 0) {
    $UserSession.text        = "No Active Users logged into Selected Host Pool"
    $UserSession.Enabled     = $false
    }
Else {
    $UserSession.BackColor   = "white"
    $UserSession.text        = "Please Select the User to be Shadowed"
    $UserSession.Enabled     = $true
    }

Foreach ($ActiveUser in $ActiveUsers) {
    $UserSession.Items.Add($ActiveUser.ActiveDirectoryUserName)
    $UserSessionHost.Items.Add($ActiveUser.Name.Split('/')[1])
    $UserSessionID.Items.Add($ActiveUser.Name.Split('/')[2])
    }

}

Function ShadowUserSession {

$UserUPN                     = $UserSession.Text
$AVDSessionHost              = $UserSessionHost.Items.Item($UserSession.SelectedIndex)
$AVDSessionID                = $UserSessionID.Items.Item($UserSession.SelectedIndex)

If ($TakeControl.Checked -eq $True) {
    $AllowControl            = "Yes"
    }
Else {
    $AllowControl            = "No"
    }

$ShadowUser.Dispose()

Write-Host ; Write-Host $(Get-Date -Format HH:mm:ss:) -ForegroundColor Gray -NoNewLine ; Write-Host " Shadowing User " -NoNewline
Write-Host $UserUPN -ForegroundColor Cyan -NoNewline ; Write-Host ", Connected to " -NoNewline
Write-Host $AVDSessionHost -ForegroundColor Green -NoNewline ; Write-Host " on Session ID " -NoNewline
Write-Host $AVDSessionID -ForegroundColor Gray -NoNewline

If ($UseMSTSC -eq $true) {
    If ($AllowControl -eq "Yes") {
        Write-Host " with Remote Control " -NoNewline ; Write-Host "Enabled" -ForegroundColor Green
        Start-Process -FilePath "mstsc.exe" -ArgumentList "/v:$AVDSessionHost /shadow:$AVDSessionID /control"
        }
        Else {
        Write-Host " with Remote Control " -NoNewline ; Write-Host "Disabled" -ForegroundColor Red
        Start-Process -FilePath "mstsc.exe" -ArgumentList "/v:$AVDSessionHost /shadow:$AVDSessionID"
        }
    }
Else {
    Start-Process -FilePath "msra.exe" -ArgumentList "/OfferRa $($AVDSessionHost) $($UserUPN):$($AVDSessionID)"
    }
}

[void]$ShadowUser.ShowDialog()

@GarryDown
Copy link
Owner

Please download the new version I have just uploaded, should say v3.1

@L1mbusFr1ng3
Copy link
Author

Awesome. Thank you.
I just ran the code with my updated variables and got this.

Gather_HostPools : The term 'Gather_HostPools' is not recognized as the name of a cmdlet, function, script file, or operable program.
Check the spelling of the name, or if a path was included, verify that the path is correct and try again.
At C:\Users\ericd\Downloads\New Script\AVD Shadowing.ps1:254 char:5

  • Gather_HostPools
    
  • ~~~~~~~~~~~~~~~~
    
    • CategoryInfo : ObjectNotFound: (Gather_HostPools:String) [], CommandNotFoundException
    • FullyQualifiedErrorId : CommandNotFoundException

@GarryDown
Copy link
Owner

Ok, can you do this while I work out the issue

Where you set the Subscription replicate the subscription name so you variable will look like this

$AVDSubscriptions = @('LAMPS PLUS','LAMPS PLUS')

This is currently working for me and I'll look into the issue when only one subscription is listed

@L1mbusFr1ng3
Copy link
Author

Ok made the change. Much better. Now it at least loads the UI. But now regardless of which LAMPS PLUS I choose it crashes. When I select the second one it just freezes. When I select the first one I get this error. Let me know if you need more of the output.

image

@L1mbusFr1ng3
Copy link
Author

Here is a sample script I was working on that has no problem getting the active user sessions and host pool. Maybe this will help with your current code to make a fix? If not maybe you can tell me how to take what this script outputs but add something to get the corresponding host name to the active user session? Once I have the host name and session ID filled I can combine with your code. But I can't get those two fields.

Either your script or a fix for mine and I'd be all set. Dedicating my day to this so let me know. Thanks again for the prompt responses.

My sample code I was working on to fix yours. This gets the sessions and host-pool I define, which would be find to have a seperate script for each host-pool in my use case.

Add-Type -AssemblyName PresentationFramework

Install required module if not already installed

Install-Module -Name Az.DesktopVirtualization

Connect to Azure account

Connect-AzAccount

Set the context to the appropriate subscription

Set-AzContext -SubscriptionId "53522dc9-55fa-48fa-a0e7-73d261d61f71"

Set the target resource group

$resourceGroupName = "RG-AVD"

Create a simple WPF form

$window = New-Object System.Windows.Window
$window.Title = "AVD User Sessions"
$window.Width = 800
$window.Height = 600

Create a ListView

$listView = New-Object System.Windows.Controls.ListView
$listView.View = (New-Object System.Windows.Controls.GridView)

Create columns for the ListView

$listView.View.Columns.Add((New-Object System.Windows.Controls.GridViewColumn -Property @{Header = "User Session"; Width = 200; DisplayMemberBinding = New-Object System.Windows.Data.Binding 'UserPrincipalName'}))
$listView.View.Columns.Add((New-Object System.Windows.Controls.GridViewColumn -Property @{Header = "Host Pool"; Width = 200; DisplayMemberBinding = New-Object System.Windows.Data.Binding 'HostPoolName'}))
$listView.View.Columns.Add((New-Object System.Windows.Controls.GridViewColumn -Property @{Header = "Host Name"; Width = 200; DisplayMemberBinding = New-Object System.Windows.Data.Binding 'HostName'}))

Get all AVD host pools in the specified resource group

$avdHostPools = Get-AzWvdHostPool -ResourceGroupName $resourceGroupName

Create an empty list to store the data

$dataList = New-Object System.Collections.Generic.List[Object]

Collect the user session data

if ($avdHostPools -ne $null) {
foreach ($avdHostPool in $avdHostPools) {

    # Get user sessions for the current host pool
    $userSessions = Get-AzWvdUserSession -ResourceGroupName $resourceGroupName -HostPoolName $avdHostPool.Name
    if ($userSessions -ne $null) {
        foreach ($session in $userSessions) {
            $dataList.Add([PSCustomObject]@{
                UserPrincipalName = $session.UserPrincipalName
                HostPoolName = $avdHostPool.Name
                HostName = $session.HostName
            })
        }
    }
}

} else {
$window.Close()
Write-Host "No AVD Host Pools found in resource group '$resourceGroupName'."
}

Populate the ListView with data

$dataList | ForEach-Object {
$listView.Items.Add($_)
}

Double-click event handler

$listView.Add_MouseDoubleClick({
$selectedItem = $listView.SelectedItem
if ($selectedItem -ne $null) {
$user = $selectedItem.UserPrincipalName
$hostPool = $selectedItem.HostPoolName
$host = $selectedItem.HostName
[System.Windows.MessageBox]::Show("User: $usernHost Pool: $hostPoolnHost: $host", "Row Double-Clicked")
}
})

$window.Content = $listView

Display the window

$window.ShowDialog() | Out-Null

@GarryDown
Copy link
Owner

Changes to the connection commands in the AZ Module required a change to the commands used to connect to the correct subscription

New version of the script uploaded

@L1mbusFr1ng3
Copy link
Author

Hi Gary it works great. I may be adding a refresh button and some search functions, if I do I will send your way.
One problem I am working on first that maybe you can help with. I think I am going to have each host pool and active session list load beforehand. Or make the gather hostpool and hostpoolselection function multithreaded.

Currently, it works but if I switch between host pools after 1 successfully loads the whole thing freezes. GUI and Console freeze, with no error. I tried waiting a long time and also my session lists aren't that large. Any thoughts on fixing that? With that fixed, the rest will be smooth sailing.

@L1mbusFr1ng3
Copy link
Author

Hi Gary,
Any chance you can help with the freezing. When bouncing between host pools. Sometimes changing only twice and it freezes. Other times 3.

Maybe you can revise it to fetch ALL host pool's active sessions and store them so they are cached? Then just add a refresh button? I tried but I'm failing. Could you perhaps do that?

I'd be willing to send you some cash do make these changes! Let me know your thoughts.

Thanks,
Eric
[email protected]

@GarryDown
Copy link
Owner

I'll take a look and see what the options are

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants