Search code examples
powershellpowershell-remoting

Converting a value to corresponding text


I am trying to get my script finished for checking powershell versions on remote machines, and I am now down to one last part, I am getting a version number of the file back from powershell but I am looking for a way to turn 6.2.1200.XXX to Version 3, my script thus far is

Foreach ($Computer in $Computers)
{
    Try
    {
        Write-Host "Checking Computer $Computer"
        $path = "\\$Computer\C$\windows\System32\WindowsPowerShell\v1.0\powershell.exe"
        if (test-path $path)
        {
            Write-host "Powershell is installed::"
            [bool](ls $path).VersionInfo
            Write-host " "
            Write-host "Powershell Remoting Enabled::"
            [bool](Test-WSMan -ComputerName $Computer -ErrorAction SilentlyContinue)
        }
        else
        {
            Write-Host "Powershell isn't installed" -ForegroundColor 'Red'
        }
        Write-Host "Finished Checking Computer $Computer"
    }

Solution

  • The file versions which include the revision, might change as updates get installed, but the first 3 numbers should be useful. You can cast as a [version] or you can just use a simple split or replace to get rid of the build.

    You could then make a hashtable with version numbers as keys and PS versions as values.

    $fileVer = [version](Get-Item $path).VersionInfo
    $myVer = "{0}.{1}.{2}" -f $fileVer.Major,$fileVer.Minor,$fileVer.Build
    
    $verTable = @{
        '6.3.1200' = 3
        '6.3.9600' = 4
    }
    
    $psVer = $verTable[$myVer]
    

    Otherwise, if you've determined that PowerShell remoting is in fact enabled, another way would be to just ask it:

    $prEnabled = [bool](Test-WSMan -ComputerName $Computer -ErrorAction SilentlyContinue)
    if ($prEnabled) {
        $psVer = Invoke-Command -ComputerName $computer -ScriptBlock { $PSVersionTable.PSVersion.Major }
    }
    

    Alternatives for setting $myVer:

    String substitution:

    $fileVer = [version](Get-Item $path).VersionInfo
    $myVer = "$($fileVer.Major).$($fileVer.Minor).$($fileVer.Build)"
    

    Replace (regular expression):

    $fileVer = (Get-Item $path).VersionInfo
    $myVer = $fileVer -replace '\.\d+$',''
    # replaces the last dot and any digits with nothing
    

    Split with range:

    $fileVer = (Get-Item $path).VersionInfo
    $myVer = ($fileVer -split '\.')[0..2]
    # splits on a literal dot, then uses a range to get the first 3 elements of the array
    

    Using switch -wildcard (credit to Ansgar Wiechers):

    $fileVer = (Get-Item $path).VersionInfo.ProductVersion
    $myVer = switch -Wildcard ($fileVer) {
        '6.3.1200.*' { 3 }
        '6.3.9600.*' { 4 }
    }