Tuesday, October 29, 2013

PowerShell script to list installed updates

I've built a script that will allow a user (no need to elevate unless using the execution policy bypass option) to get a list of the system's installed updates and outputs them to a spreadsheet (CSV), console, or be piped to some other function. Still working on listing the superseded updates, as they tend to be numerous and nested.

I will try to find a style sheet for displaying code similar to the Windows Server 2012+ PowerShell ISE, but for now...

#Get-AllInstalledUpdates.ps1 version 0.2.1
#Author: James Carter
#Used for determining currently installed updates that are NOT staged and are reported as enabled and used, including Windows OS and Application updates like service packs.

$ErrorActionPreference = "stop"

#Bypass whatever Execution Policy that might be in force for the duration of the process.
#Set-ExecutionPolicy -ExecutionPolicy Bypass -Scope Process

#File browser function creation (used to generate GUI file browser so user can select CSV location)
function Invoke-FileBrowser
{
      param([string]$Title,[string]$Directory,[string]$DefaultFileName,[string]$Filter="All Files (*.*)|*.*")
      [System.Reflection.Assembly]::LoadWithPartialName("System.Windows.Forms") | Out-Null
      $FileBrowser = New-Object System.Windows.Forms.SaveFileDialog
      $FileBrowser.InitialDirectory = $Directory
      $FileBrowser.Filter = $Filter
      $FileBrowser.Title = $Title
      $FileBrowser.FileName = $DefaultFileName
      $Show = $FileBrowser.ShowDialog()
      If ($Show -eq "OK")
      {
            Return $FileBrowser.FileName
      }
      Else
      {
            Write-Error "Restore cancelled by user."
      }
}

#File browser invocation to select target file location (comment this out if you plan on using a fixed file name and location below)
$file = Invoke-FileBrowser -Title "Browse" -DefaultFileName "CurrentlyInstalledUpdates.csv" -Filter "All Files (*.csv)|*.csv"

#Begin object creation using Update Searcher to iterate through updates on the current host ("IsInstalled=1" to find what is installed, with a "0" to help find what's missing).
$searcher = New-Object -ComObject Microsoft.Update.Searcher
$searcher.Online = $true
$searcher.ServerSelection = 1
$results = $searcher.Search('IsInstalled=1')

#Show results to console
#$results.Updates | Select-Object @{Name="KBArticleIDs"; Expression={$_.KBArticleIDs}}, @{Name="SecurityBulletinIDs"; Expression={$_.SecurityBulletinIDs}}, Title, MsrcSeverity, @{Name="SupercededUpdateIDs"; Expression={$_.SupercededUpdateIDs}}, @{Name="UpdateID"; Expression={$_.Identity.UpdateID}}

#Show count of updates installed to console
#$results.Updates.Count

#Output results to a fixed CSV file (comment this out if you plan on using the Invoke-FileBrowser method from above).
#$results.Updates | Select-Object @{Name="KBArticleIDs"; Expression={$_.KBArticleIDs}}, @{Name="SecurityBulletinIDs"; Expression={$_.SecurityBulletinIDs}}, Title, MsrcSeverity, @{Name="SupercededUpdateIDs"; Expression={$_.SupercededUpdateIDs}}, @{Name="UpdateID"; Expression={$_.Identity.UpdateID}} | Export-Csv d:\Storage\allinstalledupdates.csv

#Write results to CSV at user selected location
$results.Updates | Select-Object @{Name="KBArticleIDs"; Expression={$_.KBArticleIDs}}, @{Name="SecurityBulletinIDs"; Expression={$_.SecurityBulletinIDs}}, Title, MsrcSeverity, @{Name="SupercededUpdateIDs"; Expression={$_.SupercededUpdateIDs}}, @{Name="UpdateID"; Expression={$_.Identity.UpdateID}} | Export-Csv $file

No comments: