Need some help in fixing PowerShell to export Windows Update to. CSV file ?

Welcome Forums General PowerShell Q&A Need some help in fixing PowerShell to export Windows Update to. CSV file ?

This topic contains 4 replies, has 3 voices, and was last updated by

 
Participant
5 months, 1 week ago.

  • Author
    Posts
  • #138937

    Participant
    Topics: 16
    Replies: 17
    Points: 141
    Rank: Participant

    Hi All,

    I need to get the list of the server last windows update patch from multiple different OU and then export it as in CSV file with the below column:

    ServerName, Last Time Update Installed, KB Number, KB Update Name

    This is the script for multiple OU processing, but somehow the result is still blank.CSV file?

    $CsvFile = 'C:\Result.csv'
    $key = 'SOFTWARE\Microsoft\Windows\CurrentVersion\WindowsUpdate\Auto Update\Results\Install'
    $keytype = [Microsoft.Win32.RegistryHive]::LocalMachine

    $OUList = @(
    "OU=TEST Servers,OU=MyDomain Testing,DC=MyDomain,DC=com"
    "OU=PROD Servers,OU=Servers,OU=MyDomain,DC=MyDomain,DC=com"
    "OU=PROD Servers,OU=Servers,OU=New Company,DC=MyDomain,DC=com"
    )

    $OUList | ForEach-Object {
    $OU = $_
    $Computers = Get-ADComputer -Filter {Enabled -eq $True -and OperatingSystem -like "*Server*"} -SearchBase $OU |
    Select-Object -ExpandProperty DNSHostName |
    ForEach-Object {
    If (Test-Connection $_ -Count 1 -Quiet) {
    $_
    }
    Else {
    Write-Host "Cannot reach $($_)" -ForegroundColor Red
    }
    }
    ForEach ($computer in $Computers) {
    Try {
    $remoteBase = [Microsoft.Win32.RegistryKey]::OpenRemoteBaseKey($keytype, $computer)
    $regKey = $remoteBase.OpenSubKey($key)
    $keyValue = $regkey.GetValue('LastSuccessTime')
    Write-Host "
    Write-Host "$($computer): last time updates were installed was $($keyValue)"
    }
    Catch {
    $ | Write-Error
    }
    Finally {
    If ($regKey) {$regKey.Close()}
    }
    }
    } | Export-Csv -Path $Csvfile -NoTypeInformation

    I'd like to know if the below result is possible just like running Get-HotFix locally on each server:

    ServerName, Last Time Update Installed, KB Number, KB Update Name, InstalledBy
    PRODSQL01-VM, 31/12/2018 02:46:55, KB4462930, Cumulative Update, NT AUTHORITY\SYSTEM
    PRODSQL02-VM, 18/12/2018 12:00:00 AM, KB4471324, Security Update, DOMAIN\SVC_SCCM
    PRODDC01-VM, 16/1/2019 02:16:31, KB4343669, Cumulative Update, DOMAIN\SVC_SCCM
    PRODDC02-VM, 13/1/2018 03:00:00 AM, KB4457146, Security Update, DOMAIN\Admin-Staff1

    Any help would be greatly appreciated.

    Thanks,

  • #138943

    Participant
    Topics: 3
    Replies: 48
    Points: 113
    Helping Hand
    Rank: Participant

    Using the

    Invoke-Command

    cmdlet, you could fashion your code to loop through every computer in the target OU.

    This is just a example of how I accomplished a similar project a few weeks back:

    $servers = Get-Content -Path '.\hosts.txt'
    
    Invoke-Command -ComputerName $servers -ScriptBlock {
    
        Get-HotFix | Select-Object -Property PSComputerName, Description, HotFixID, InstalledOn
    
        }

    You can pipe the above code to whatever type of output you are looking for.

    I am curious as to why you are trying to pull this info from the registry using .NET methods though.

  • #138945

    Participant
    Topics: 1
    Replies: 1430
    Points: 2,127
    Helping Hand
    Rank: Community Hero

    It's even easier than that. Get-Hotfix supports the parameter -ComputerName. So you actually only need something like this:

    $CsvFile = 'C:\Result.csv'
    $OUList = @(
        'OU=TEST Servers,OU=MyDomain Testing,DC=MyDomain,DC=com'
        'OU=PROD Servers,OU=Servers,OU=MyDomain,DC=MyDomain,DC=com'
        'OU=PROD Servers,OU=Servers,OU=New Company,DC=MyDomain,DC=com'
    )
    
    $Result = ForEach ($OU in $OUList) {
        Get-ADComputer -Filter {Enabled -eq $True -and OperatingSystem -like "*Server*"} -SearchBase $OU |
            ForEach-Object {
                If (Test-Connection $_.Name -Count 1 -Quiet) {
                    Get-HotFix -ComputerName $_.Name | Select-Object -Property PSComputerName, Description, HotFixID, InstalledOn, InstalledBy
                }
        }
    } 
    $Result |
        Export-Csv -Path $Csvfile -NoTypeInformation
  • #138955

    Participant
    Topics: 16
    Replies: 17
    Points: 141
    Rank: Participant

    Thanks all for the suggestion.

    I need the last date of the patch applied, hence I put the key $keyValue = $regkey.GetValue('LastSuccessTime').

    So I can now change that into:

    Get-HotFix -ComputerName $_.Name | Sort-Object InstalledOn | Select-Object -Property PSComputerName, Description, HotFixID, InstalledOn, InstalledBy -Last 1
    Would that be correct?
  • #138957

    Participant
    Topics: 16
    Replies: 17
    Points: 141
    Rank: Participant

    What would be the difference with the WMI method?

    Get-WmiObject -Class "Win32_QuickFixEngineering" -ComputerName $_.Name-ErrorAction Stop |
                Select-Object -Property `
                    @{Name="ComputerName"; Expression={$Server}},
                    "Description",
                    "HotfixID",
                    @{Name="InstalledOn"; Expression={([DateTime]($_.InstalledOn)).ToLocalTime()}},
                    "Error"
            "OK."

The topic ‘Need some help in fixing PowerShell to export Windows Update to. CSV file ?’ is closed to new replies.