Get the last Windows Update install date using PowerShell
Solution 1
Does Get-HotFix
meet your needs?
Get-HotFix -ComputerName $_.Name | Measure-Object InstalledOn -Maximum
Your performance issues could be coming from Get-ADComputer
. I'd do some troubleshooting to see which piece is causing you problems.
Solution 2
Tim Ferrill already provided you the answer but for the record you could have done something like this
$ScriptBlock = {
$hash=@{}
$Session = New-Object -ComObject Microsoft.Update.Session
$Searcher = $Session.CreateUpdateSearcher()
$hash[$env:Computername] = $Searcher.QueryHistory(1,1) | select -ExpandProperty Date
$hash
}
Invoke-Command -ComputerName $serverlist -ScriptBlock $ScriptBlock
This would get you something like
Name Value
---- -----
Server1 5/16/2014 2:11:42 PM
Server2 4/14/2014 1:55:03 PM
Server3 5/6/2014 5:36:51 PM
Keltari
Updated on July 15, 2022Comments
-
Keltari almost 2 years
I am trying to write a PowerShell script that will query all the servers in Active Directory and see the last date a Windows Update was applied.
I was having some trouble, so just to get it done, I created two scripts, one in Powershell to get the servers and the other in VBScript to query the last date. I found a this Powershell module that allows me to query the last install date, but it is extremely slow, especially on remote servers.
Here is the PS code:
Get-ADComputer -Filter 'OperatingSystem -like "*Server*"' -Properties * | Select-Object Name | Sort-Object Name | ForEach-Object { Get-WUHistory -ComputerName $_.Name | Sort-Object Date,ComputerName -Descending | Select-Object -First 1 }
Its so slow, its practically unusable.
I have some VBScript which I cobbled together that is much faster. See below:
On Error Resume Next Set fso = CreateObject("Scripting.FileSystemObject") Set file = fso.OpenTextFile ("servers.csv", 1) server = "" Do Until file.AtEndOfStream line = file.Readline server = line 'wscript.echo server Set objSession = CreateObject("Microsoft.Update.Session", server) If Err.Number <> 0 Then 'WScript.Echo server & " Error: " & Err.Number & " Error (Hex): " & Hex(Err.Number) & " Source: " & Err.Source & " Description: " & Err.Description WScript.Echo server & " Communications Error" Err.Clear Else Set objSearcher = objSession.CreateUpdateSearcher Set colHistory = objSearcher.QueryHistory(1, 1) For Each objEntry in colHistory Wscript.Echo server & " " & objEntry.Date Next End If Loop file.Close
Is there an easy way to get the speed of the VBScript into the Powershell code?
Here is the working Powershell code (modified again) if anyone is interested:
$ErrorActionPreference= 'silentlycontinue' Get-ADComputer -Filter 'OperatingSystem -like "*Server*"' -Properties * | Select-Object Name | ForEach-Object { If (Test-Connection $_.Name -Count 1){ Get-HotFix -ComputerName $_.Name | Sort-Object InstalledOn -Descending | Select-Object -First 1 } else { Write-host $_.Name " Connection Error" } } | Sort-Object InstalledOn
-
Keltari about 10 yearsIf you mean Get-ADComputer, then no thats pretty quick. The slowness is definitely from Get-WUHistory. Im trying get-hotfix now.
-
Tim Ferrill about 10 yearsYeah, that. Where'd I put that coffee?
-
Keltari about 10 yearsThis works at a reasonable speed. Putting my amended script in the question.
-
Keltari about 10 yearsHm. Ill check this out
-
Admin over 8 yearsGet-Hotfix does require Powershell 3.0 or greater, but a fair enough trade-off and as a bonus meets the requirement for many scenarios where a course-grained one-liner is enough.