Powershell Invoke-Command Check RDP Port and Formatting Output

This topic contains 1 reply, has 2 voices, and was last updated by  Jonathan Warnken 2 years ago.

  • Author
    Posts
  • #30389

    StackExchangeUser6
    Participant

    I have written this script to check a list of servers or server for Ping and Port 3389 state. The requirement is I have to Invoke-Command to a remote computer and then query the Ping and port state of the actual problem server.

    I am able to get the output formatted as I want to but I need help in querying the RDP port state correctly as I am unable to get that working inside a -ScriptBlock statement.

    Here is the code I have:

    [CmdletBinding()]
    Param
    (
        [Parameter(Mandatory=$True)]
        [ValidateNotNullOrEmpty()]
        [string[]]$ComputerName,
    
        [Parameter(Position=1)]
        [ValidateNotNullOrEmpty()]
        [ValidateRange(1,65535)]
        [Int[]]$Port
    )
    
    Begin
    {
        $Report = @()
    }
    
    Process
    {
        Foreach ($Computer in $ComputerName)
        {
            $Res = Invoke-Command -ComputerName $HopboxIP -Credential $Creds `
                        -ScriptBlock { param ($Computer) Get-WmiObject Win32_PingStatus -Filter "Address = '$Computer'" | `
                                Select @{Label="Source";Expression={$Computer}},IPV4Address,@{Label="Status";Expression={If($_.StatusCode -ne 0) { "Failed"} Else {"Success"}}}} -ArgumentList $Computer
    
            $RDPres = Invoke-Command -ComputerName $HopboxIP -Credential $Creds `
                        -ScriptBlock { (New-Object System.Net.Sockets.TCPClient -ArgumentList $Computer,3389) | `
                                Select @{Label="Connected";Expression={If($_.Connected -eq "True") {"Listening"} Else {"Filtered"}}}}
    
            $Res | select Source, IPV4Address, Status | Format-Table -AutoSize | Out-Null
            $RDPres | select Connected | Format-Table -AutoSize | Out-Null
    
            $Report += New-Object PSObject -Property @{
                            'IPAddress' = $Res.IPV4Address
                            'ComputerName' = $Res.Source
                            'Ping' = $Res.Status
                            'Port(3389)' = $RDPRes.Connected
                          }
    
     }   
    }
       End 
       { 
          Return $Report      
        }
    

    Also, I am unable to skip the port check of a server if the Ping fails for it and the result should show as Ping Failed and Port Filtered.

    Please help in optimizing this script for the RDP port check functionality and also if someone can help with Try and Catch statements inside a ScriptBlock, it will be a great learning for me.

    Thanks!!

  • #30393

    Jonathan Warnken
    Participant

    Welcome to the wonderful world of Powershell Remoting, you have a classic double hop authentication issue. Don Jones has a great resource "Secrets of PowerShell Remoting" that is available free and on this site under Resources > Free Ebooks. There are very vaild security reasons why powershell and the underlying WINRM support remote connections this way. There are ways to change the configuration but you should fully understand the implications before doing so. If you run the script on the "Hopbox" directly rather then invoking it remotely you should be successful.

    Here is a simple way to only do the port check if the ping is successful

    [CmdletBinding()]
    Param
    (
        [Parameter(Mandatory=$True)]
        [ValidateNotNullOrEmpty()]
        [string[]]$ComputerName,
    
        [Parameter(Position=1)]
        [ValidateNotNullOrEmpty()]
        [ValidateRange(1,65535)]
        [Int[]]$Port
    )
    
    Begin
    {
        $Report = @()
    }
    
    Process
    {
        Foreach ($Computer in $ComputerName)
        {
            $Res = Invoke-Command -ComputerName $HopboxIP -Credential $Creds `
                        -ScriptBlock { param ($Computer) Get-WmiObject Win32_PingStatus -Filter "Address = '$Computer'" | `
                                Select @{Label="Source";Expression={$Computer}},IPV4Address,@{Label="Status";Expression={If($_.StatusCode -ne 0) { "Failed"} Else {"Success"}}}} -ArgumentList $Computer
            $Res | select Source, IPV4Address, Status | Format-Table -AutoSize | Out-Null
            If($res -eq "Success"){
                $RDPres = Invoke-Command -ComputerName $HopboxIP -Credential $Creds `
                            -ScriptBlock { (New-Object System.Net.Sockets.TCPClient -ArgumentList $Computer,3389) | `
                                    Select @{Label="Connected";Expression={If($_.Connected -eq "True") {"Listening"} Else {"Filtered"}}}}
                $RDPres | select Connected | Format-Table -AutoSize | Out-Null
    
                $Report += New-Object PSObject -Property @{
                            'IPAddress' = $Res.IPV4Address
                            'ComputerName' = $Res.Source
                            'Ping' = $Res.Status
                            'Port(3389)' = $RDPRes.Connected
                          }
            }Else{
                $Report += New-Object PSObject -Property @{
                            'IPAddress' = $Res.IPV4Address
                            'ComputerName' = $Res.Source
                            'Ping' = $Res.Status
                            'Port(3389)' = "Unknown"
                          }
            }
    
    
     }   
    }
       End 
       { 
          Return $Report      
        }
    

You must be logged in to reply to this topic.