VMware Cloud Community
piercj2
Enthusiast
Enthusiast
Jump to solution

General VM info

Hi,

I'm trying to create a script that will provide some General VM info.

I'm collecting this information as I'm about to perform an SRM failover and want to have as much info about each VM as is necessary in case I need to rebuild anything from Scratch :smileycry:

I've put the following together and it works except

  1. I'd like to export it to a csv
  2. in the case of a VM with multiple HDD's or multiple NIC's, I'd like the output to be in separate columns

For example, my script produced the following output for HDD's in the VM

HDD Info     : {@{Name=Hard disk 1; Filename=[VMFS_IRL_1] Server1/Server1_2.vmdk; CapacityGB=40}, @{Name=Hard disk 2;

               Filename=[VMFS_IRL_1] Server1/Server1_1.vmdk; CapacityGB=90}}

I would prefer the following for each VM's Hard Disk info

HDD1 NameHDD1 PathHDD1 CapacityGBHDD2 NameHDD2 PathHDD2 CapacityGBHDD3 Name
Hard disk 1[VMFS_IRL_1] Server1/Server1_2.vmdk40Hard disk 2[VMFS_IRL_1] Server1/Server1_1.vmdk90

Here's the script

$content = get-vm (Get-Content C:\Temp\vmList.txt)

foreach($Computer in $content){

          

   $GeneralProp=[ordered]@{

        'ComputerName'=$computer.Name;

        'PowerState'=$Computer.PowerState;

        'OS'=$Computer.GuestId;

        'VMware Tools'=$Computer.Guest.ToolsVersion;

        'Num CPU'=$Computer.NumCpu;

        'Memory GB'=$Computer.MemoryGB;

        'Host'=$Computer.VMHost;

        'ResourcePool'=$Computer.ResourcePool;

        'Num HDD'=$Computer.HardDisks.Count;

        'HDD Info'=$Computer | Get-HardDisk | select Name, Filename, CapacityGB;

        'Num NIC'=$Computer.NetworkAdapters.Count;

        'NIC Info'=$Computer | Get-VirtualPortGroup | select VirtualSwitch, vlanID, Name;

        'NIC IP'=$Computer.Guest.IPAddress;

    }

$Obj=New-Object -TypeName PSObject -Property $GeneralProp

Write-Output $Obj

}

   

Any help would be great,

Thanks

0 Kudos
1 Solution

Accepted Solutions
LucD
Leadership
Leadership
Jump to solution

You should collect each $obj in an array, and then write the array to a CSV.

Something like this

$content = get-vm (Get-Content C:\Temp\vmList.txt)

$report = @()

foreach($Computer in $content){

   $GeneralProp=[ordered]@{

        'ComputerName'=$computer.Name;

        'PowerState'=$Computer.PowerState;

        'OS'=$Computer.GuestId;

        'VMware Tools'=$Computer.Guest.ToolsVersion;

        'Num CPU'=$Computer.NumCpu;

        'Memory GB'=$Computer.MemoryGB;

        'Host'=$Computer.VMHost;

        'ResourcePool'=$Computer.ResourcePool;

   }

   $hdd = 1

   $Computer | Get-HardDisk | foreach {

        $GeneralProp.Add("HDD$($hdd) Name",$_.Name)

        $GeneralProp.Add("HDD$($hdd) Path",$_.FileName)

        $GeneralProp.Add("HDD$($hdd) Capacity",$_.CapacityGb)

        $hdd++

   }

   $nic = 1

   $Computer | Get-VirtualPortGroup | foreach {

        $GeneralProp.Add("NIC$($nic) vSwitch",$_.VirtualSwitch)

        $GeneralProp.Add("NIC$($nic) PortGroup",$_.Name)

        $GeneralProp.Add("NIC$($nic) VLAN ID",$_.VlanID)

        $GeneralProp.Add("NIC$($nic) IP", $Computer.Guest.IPAddress[$nic-1])

        $nic++

    }

   $report += New-Object -TypeName PSObject -Property $GeneralProp

}

$report | Export-Csv C:\Temp\SRM\VMdetails.csv -NoTypeInformation


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

View solution in original post

0 Kudos
13 Replies
LucD
Leadership
Leadership
Jump to solution

Try like this

$content = get-vm (Get-Content C:\Temp\vmList.txt)

foreach($Computer in $content){

   $GeneralProp=[ordered]@{

        'ComputerName'=$computer.Name;

        'PowerState'=$Computer.PowerState;

        'OS'=$Computer.GuestId;

        'VMware Tools'=$Computer.Guest.ToolsVersion;

        'Num CPU'=$Computer.NumCpu;

        'Memory GB'=$Computer.MemoryGB;

        'Host'=$Computer.VMHost;

        'ResourcePool'=$Computer.ResourcePool;

        'Num HDD'=$Computer.HardDisks.Count;

        'HDD Info'=$Computer | Get-HardDisk | select Name, Filename, CapacityGB;

        'Num NIC'=$Computer.NetworkAdapters.Count;

        'NIC Info'=$Computer | Get-VirtualPortGroup | select VirtualSwitch, vlanID, Name;

        'NIC IP'=$Computer.Guest.IPAddress;

   }

   $i = 1

   $Computer | Get-HardDisk | %{

        $GeneralProp.Add("HDD$($i) Name",$_.Name)

        $GeneralProp.Add("HDD$($i) Path",$_.FileName)

        $GeneralProp.Add("HDD$($i) Capacity",$_.CapacityGb)

        $i++

   }

   $Obj=New-Object -TypeName PSObject -Property $GeneralProp

   $Obj


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
piercj2
Enthusiast
Enthusiast
Jump to solution

Hi LucD,

Thanks for the advice on this. What you advised worked and I was able to use it to also get some needed Network Config information.

The script is almost working 100%, there's just one small issue. It only returns the information for a single VM, despite a list of VM's being given in C:\Temp\vmList.txt

The line $content = get-vm (Get-Content C:\Temp\vmList.txt) works.

When I output $content I see the entire list of VM names, their PowerState, Num CPUs and MemoryGB

I would expect the foreach($computer in $content) loop to iterate for every VM but, it doesn't for some reason.

I just get the results that I need for a single (random) VM in the list.

Can you see what's wrong with the following ?

$content = get-vm (Get-Content C:\Temp\vmList.txt)

foreach($Computer in $content){

   $GeneralProp=[ordered]@{

        'ComputerName'=$computer.Name;

        'PowerState'=$Computer.PowerState;

        'OS'=$Computer.GuestId;

        'VMware Tools'=$Computer.Guest.ToolsVersion;

        'Num CPU'=$Computer.NumCpu;

        'Memory GB'=$Computer.MemoryGB;

        'Host'=$Computer.VMHost;

        'ResourcePool'=$Computer.ResourcePool;

   }

 

   $hdd = 1

   $Computer | Get-HardDisk | foreach {

        $GeneralProp.Add("HDD$($hdd) Name",$_.Name)

        $GeneralProp.Add("HDD$($hdd) Path",$_.FileName)

        $GeneralProp.Add("HDD$($hdd) Capacity",$_.CapacityGb)

        $hdd++

   }

   $nic = 1

   $Computer | Get-VirtualPortGroup | foreach {

        $GeneralProp.Add("NIC$($nic) vSwitch",$_.VirtualSwitch)

        $GeneralProp.Add("NIC$($nic) PortGroup",$_.Name)

        $GeneralProp.Add("NIC$($nic) VLAN ID",$_.VlanID)

        $GeneralProp.Add("NIC$($nic) IP", $Computer.Guest.IPAddress[$nic-1])

        $nic++

    }

   $Obj=New-Object -TypeName PSObject -Property $GeneralProp

   $Obj | Export-Csv C:\Temp\SRM\VMdetails.csv -NoTypeInformation

}

0 Kudos
LucD
Leadership
Leadership
Jump to solution

You should collect each $obj in an array, and then write the array to a CSV.

Something like this

$content = get-vm (Get-Content C:\Temp\vmList.txt)

$report = @()

foreach($Computer in $content){

   $GeneralProp=[ordered]@{

        'ComputerName'=$computer.Name;

        'PowerState'=$Computer.PowerState;

        'OS'=$Computer.GuestId;

        'VMware Tools'=$Computer.Guest.ToolsVersion;

        'Num CPU'=$Computer.NumCpu;

        'Memory GB'=$Computer.MemoryGB;

        'Host'=$Computer.VMHost;

        'ResourcePool'=$Computer.ResourcePool;

   }

   $hdd = 1

   $Computer | Get-HardDisk | foreach {

        $GeneralProp.Add("HDD$($hdd) Name",$_.Name)

        $GeneralProp.Add("HDD$($hdd) Path",$_.FileName)

        $GeneralProp.Add("HDD$($hdd) Capacity",$_.CapacityGb)

        $hdd++

   }

   $nic = 1

   $Computer | Get-VirtualPortGroup | foreach {

        $GeneralProp.Add("NIC$($nic) vSwitch",$_.VirtualSwitch)

        $GeneralProp.Add("NIC$($nic) PortGroup",$_.Name)

        $GeneralProp.Add("NIC$($nic) VLAN ID",$_.VlanID)

        $GeneralProp.Add("NIC$($nic) IP", $Computer.Guest.IPAddress[$nic-1])

        $nic++

    }

   $report += New-Object -TypeName PSObject -Property $GeneralProp

}

$report | Export-Csv C:\Temp\SRM\VMdetails.csv -NoTypeInformation


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
piercj2
Enthusiast
Enthusiast
Jump to solution

LucD, you are The Man

I started thinking that I needed to collect everything in an array and, spent the last hour or two attempting it.

I only succeeded in making the code look ugly!

Your solution was simple, efficient and clean.

Thank you so mush, you've (again) made my life that bit easier

0 Kudos
LucD
Leadership
Leadership
Jump to solution

One thing to note, the Export-Csv cmdlet takes the first row in the array to determine how many columns there will be.

So if your first VM only has 1 harddisk, and subsequent VMs have more than 1 harddisk, you might be missing columns in the CSV.

One way to fix this is to sort the array on the number of properties, in descending order.

The last line could be

$report |

Sort-Object -Property {$_.Count} -Descending |

Export-Csv C:\Temp\SRM\VMdetails.csv -NoTypeInformation


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
piercj2
Enthusiast
Enthusiast
Jump to solution

I had exactly that problem :smileyconfused:

Thanks for following up before I had the chance to ask for more help

0 Kudos
piercj2
Enthusiast
Enthusiast
Jump to solution

nope, still struggling i'm afraid

I've even piped $report to get-member to see what I could use as a counter, it only lists a max of two HDDs and a single NIC (even though some VM's have multiple NICS)

more help needed please Smiley Sad

0 Kudos
LucD
Leadership
Leadership
Jump to solution

Seems to be working for me.

Can you check a couple of things ?

How many rows in $report

$report.Count

And how many properties in each row in $report

$report | %{$_.Count}


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
piercj2
Enthusiast
Enthusiast
Jump to solution

For $report.Count i'm getting a value of 67

This matches what I get for $content.Count

For $report | %{$_.Count} i don't get any value at all

What's strange is that when I try this in the ISE, it doesn't Tab Complete the command. That is, I type $report | %{$_.Cou and hit Tab, it doesn't complete the spelling for Count ?

If I output $report to the display, it 100% has all the required information

I've attached a copy of the full script that i'm running, in case there are any silly typo's or brackets in the wrong places

Thanks

0 Kudos
LucD
Leadership
Leadership
Jump to solution

My mistake, the objects that are in the array do not have a counter.

Try with these lines

$report |

    Sort-Object -Property {($_ | Get-Member -MemberType NoteProperty).Count} -Descending |

    Export-Csv C:\Temp\SRM\VMdetails.csv -NoTypeInformation


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
piercj2
Enthusiast
Enthusiast
Jump to solution

I gave it another go, still without success.

I added a Count into the array for the number of Hard Disks

foreach($Computer in $content){

   $GeneralProp=[ordered]@{

        'ComputerName'=$computer.Name;

        'PowerState'=$Computer.PowerState;

        'OS'=$Computer.GuestId;

        'VMware Tools'=$Computer.Guest.ToolsVersion;

        'Num CPU'=$Computer.NumCpu;

        'Memory GB'=$Computer.MemoryGB;

        'Host'=$Computer.VMHost;

        'ResourcePool'=$Computer.ResourcePool;

       'Num HDD'=$Computer.HardDisks.Count;

   }

Some VM's have up to 12 Hard Disks

At the end, when piping into the .csv, I tried the following

$report | Sort-Object -Property {$GeneralProp.'Num HDD'} -Descending | Export-Csv 'C:\Temp\SRM\SRM VM Details - sorted.csv'

Still the same result, only information for two Hard Disks displayed in the .csv.

I'm thinking that maybe the Details of first VM inserted into the $report array only contains 2 Hard Disks and that it's the $report array that isn't able to grow.

Does this make Sense ?

0 Kudos
LucD
Leadership
Leadership
Jump to solution

I assume you missed my last reply ?


Blog: lucd.info  Twitter: @LucD22  Co-author PowerCLI Reference

0 Kudos
piercej2
Contributor
Contributor
Jump to solution

I did indeed, sorry about that.

I need to say is once again though, you are a legend.

That last bit of help from you resolved the issue, I'm now getting 100% of the info that I need.

Attaching the full script here in case anyone else needs it

Thank you so much

0 Kudos