SimonS
SimonS

Reputation: 1973

Add member to PSCustomObject for each return

I want to read out PS Versions on the machines in my network with the following funtction:

function CheckPSVersion {
    param ([Parameter(Position = 0)][string[]]$computername)
    if (!$computername) { $computername = $env:computername }
    $y = New-Object PSCustomObject
    $computername | % {
        $x = Invoke-Command -ComputerName $_ -ScriptBlock { ($PSVersionTable.PSVersion).tostring() }
        $y | Add-Member -Membertype NoteProperty -Name Computername -value $_
        $y | Add-Member -Membertype NoteProperty -Name PowerShellVersion -Value $x
    }
    $y
}

But I have problems with Add-Member because it says "an element can't be added to "Computername" because another element with this name already exists"

my desired output would be like this:

Computername PowerShellVersion
------------ -----------------
SIS          5.0.10240.17146  
SIS1         2.0.10240.17146  
SIS2         5.0.10240.17146  
SIS3         3.0.10240.17146  
SIS4         5.0.10240.17146  

Can you help me? I really can't get my head around add-member

Upvotes: 0

Views: 10857

Answers (3)

Daniel Morritt
Daniel Morritt

Reputation: 1817

I would suggest something like Ansgar's response, I too hate the Add-Member CmdLet, it just looks clunky in code, it might help if do something like this:

$y = @()

1..10 | % {
    $y += New-Object PSObject -Property @{ ComputerName = "comp$_"; PowerShellVersion = "1.0" }
}

$y

Essentially you're creating an empty array, ignore the 1.10 loop (I only use it to give the "computers" different names), but as you can see you're adding a PSObject with custom properties to $y, resulting in an array of objects you can manipulate nicely.

Upvotes: 1

whatever
whatever

Reputation: 891

You're trying to add all the computernames to the same object, but actually need a list of objects:

$List = New-Object System.Collections.ArrayList    
$computername | % {
    $y = New-Object PSCustomObject
    $x = Invoke-Command -ComputerName $_ -ScriptBlock {($PSVersionTable.PSVersion).tostring() }
    $y | Add-Member -Membertype NoteProperty -Name Computername -value $_
    $y | Add-Member -Membertype NoteProperty -Name PowerShellVersion -Value 
    $List.Add($y)
}
$List

btw, you can replace

param ([Parameter(Position = 0)][string[]]$computername)
if (!$computername) { $computername = $env:computername }

with

param ([Parameter(Position = 0)][string[]]$computername = $env:computername )

Upvotes: 1

Ansgar Wiechers
Ansgar Wiechers

Reputation: 200293

This should suffice:

$computername | ForEach-Object {
    New-Object -Type PSCustomObject -Property @{
        Computername      = $_
        PowerShellVersion = Invoke-Command -ComputerName $_ -ScriptBlock {
                                ($PSVersionTable.PSVersion).ToString()
                            }
    }
}

Upvotes: 3

Related Questions