2

I am trying to write a powershell script that will Ping each Hostname in an OU in AD, Output a txt file of online hostnames, then using the Get-WmiObject to get a list of software on each online systems. I've tried and I can't seem to figure out how to output the pinged systems to a txt file of hostnames so I can use that file to create the software list. I know pretty much nothing about Powershell, so I've been trying to steal and borrow, but can't figure out how to make it all work. Here is what I've tried. Any help will be greatly appreciated.

Import-Module active*

$rtn = $null

Get-ADComputer -Filter * -Properties * -searchbase "OU=EnterOUstructurehere" |

ForEach-Object {

  $rtn = Test-Connection -CN $_.dnshostname -Count 1 -BufferSize 16 -Quiet

  IF($rtn -match ‘True’) {write-host -ForegroundColor green $_.dnshostname}

  ELSE { Write-host -ForegroundColor red $_.dnshostname }

}

Using Out-file to output a txt file called computers. Use Get to to pull from the computer.txt file and then:

ForEach-Object {Get-WmiObject -Class Win32_Product -Computer $_.Name} | Select-Object Name, Version | Sort-Object Name | Export-CSV "C:\Users\steven.e.hendricks\OneDrive - US Army\Desktop\Software Inventory\SoftwareInventoryfile.csv" -Append -NoTypeInformation

  • 1
    'True' is represented by `$true`, so should be `if ($rtn -eq $true)` or better just `if ($rtn)` – Daniel Jun 02 '22 at 18:35

1 Answers1

2

First, the obligatory recommendation:

  • The CIM cmdlets (e.g., Get-CimInstance) superseded the WMI cmdlets (e.g., Get-WmiObject) in PowerShell v3 (released in September 2012). Therefore, the WMI cmdlets should be avoided, not least because PowerShell (Core) v6+, where all future effort will go, doesn't even have them anymore. Note that WMI still underlies the CIM cmdlets, however. For more information, see this answer.

  • Note, however, that the CIM cmdlets use the same remoting infrastructure as PowerShell's remoting, which differs from that of the WMI cmdlets.

You're probably looking for something like this:

Get-ADComputer -Filter * -Properties * -searchbase "OU=EnterOUstructurehere" |
  Where-Object { Test-Connection -CN $_.dnshostname -Count 1 -BufferSize 16 -Quiet } |
  ForEach-Object {
    Get-WmiObject -Class Win32_Product -Computer $_.Name | 
      Select-Object Name, Version | 
      Sort-Object Name
  } |
  Export-Csv -NoTypeInformation "C:\path\to\SoftwareInventoryfile.csv"

However, note that you my want to add another property that identifies the computer name in each output object.

Also, you can speed up the operation with parallel processing, by passing an array of computer names to a single Get-WmiObject call:

$onlineComputers = 
  Get-ADComputer -Filter * -Properties * -searchbase "OU=EnterOUstructurehere" |
  Where-Object { Test-Connection -CN $_.dnshostname -Count 1 -BufferSize 16 -Quiet }

Get-WmiObject -Class Win32_Product -Computer $onlineComputers.Name | 
  Select-Object PSComputerName, Name, Version | 
  Sort-Object PSComputerName, Name |
  Export-Csv -NoTypeInformation "C:\path\to\SoftwareInventoryfile.csv"
mklement0
  • 382,024
  • 64
  • 607
  • 775
  • Nice answer! I would've personally recommended to test connectivity on ports 5985 / 5986 instead of ICMP but I believe that's up to OP to decide – Santiago Squarzon Jun 02 '22 at 18:53
  • Thanks, @Santiago. What is the advantage of testing these ports? – mklement0 Jun 02 '22 at 19:01
  • 1
    A firewall might be blocking ICMP echo requests however that wouldn't mean WinRM is blocked. One might have been able to connect to the host but it would be excluded due to an inaccurate connectivity test (this is just personal opinion) – Santiago Squarzon Jun 02 '22 at 19:04
  • Actually my bad, I'm not sure what port is used by `Get-WmiObject`. Cim uses WinRM I'm not sure if WMI uses the same ? – Santiago Squarzon Jun 02 '22 at 19:18
  • 1
    Good question, @Santiago. The blog post linked to from the linked answer just states "WMI cmdlets [...] use DCOM to access remote machines.", but I don't know what that implies. – mklement0 Jun 02 '22 at 19:26
  • 1
    You're totally right mklement0, WMI = port 135 + dynamic port allocation (RPC). – Santiago Squarzon Jun 02 '22 at 19:52