Reputation: 4339
I am trying to combine multiple object properties into one object.
When I have the following code the objects properties are combined.
$computer = gwmi win32_computersystem | select numberOfProcessors, NumberOfLogicalProcessors, HypervisorPresent
$osInfo = gwmi win32_operatingsystem | select version, caption, serialnumber, osarchitecture
Foreach($p in Get-Member -InputObject $osInfo -MemberType NoteProperty)
{
Add-Member -InputObject $computer -MemberType NoteProperty -Name $p.Name -Value $osInfo.$($p.Name) -Force
}
$computer
However, if I replace the above computer and osInfo variables with
$computer = Get-Process | Select processname, path
$osInfo = Get-Service | Select name, status
then the $computer
variables does not have the properties of the $osInfo
variable after the for loop is executed. ie: the second object is not combined with the first object.
Upvotes: 8
Views: 41627
Reputation: 72610
Your problem comes from the bad usage of Get_Member in the case of a collection.
Get-Member -InputObject ACollection
gives the members of the collection.
ACollection | Get-Member
gives the members of each element of the collection.
So in you case it will work with :
Foreach($p in ($osInfo | Get-Member -MemberType NoteProperty))
{
}
Edited
$computer
is also à collection so what do you expect. I add the code of what I think you expect.
$processes = Get-Process | Select processname, path, Id
Foreach($p in $processes)
{
$services = Get-WmiObject "Win32_Service" -filter "ProcessId=$($p.Id)"
Add-Member -InputObject $p -MemberType NoteProperty -Name "Services" -Value $(($services | % {$_.name}) -join ',') -Force
}
$processes
Upvotes: 2
Reputation: 801
The original code deals with cmdlets that returns two single objects relating to the same source.
You're trying to use it with cmdlets that return arrays of multiple objects.
The following basically merges the two arrays.
$computer = 'Server01'
$collection = @()
$services = Get-Service | Select name, status
$processes = Get-Process | Select processname, path
foreach ($service in $services) {
$collection += [pscustomobject] @{
ServiceName = $service.name
ServiceStatus = $service.status
ProcessName = ""
ProcessPath = ""
}
}
foreach ($process in $processes) {
$collection += [pscustomobject] @{
ServiceName = ""
ServiceStatus = ""
ProcessName = $process.processname
ProcessPath = $process.path
}
}
$collection
Personally, I'd just use the two lines for $services
and $processes
and be done.
Upvotes: 6