Sicherheitshinweis

Die hier bereitgestellten Skripte sind stets auf eigene Gefahr anzuwenden!
Daher immer erst mit einem nicht-kritischen System oder in einer Testumgebung ausführlich testen!


Einleitung

Ein WSUS muss nicht zwingend re-installiert werden und wird auch seitens Microsoft generell nicht empfohlen. Daher bietet sich eher eine Zurücksetzung sämtlicher Updatedateien in der Datenbank (Metadaten) an. Denn über die Jahre haben sich in den meisten WSUS-Umgebungen Unmengen an Metadaten angesammelt, die durch den „Assistent für die Serverbereinigung“ nicht automatisch mit bereinigt bzw. entfernt werden.

Anwendungsbeispiel:

Im Normalfall werden nur die entsprechenden Produkte oder Klassifizierungen de-selektiert und man denkt, dass die Metadaten und schlussendlich auch der Content sich regelmäßig von den Altlasten befreien werden... 

Dem ist aber nicht so und so verbleiben die unnötigen Metadaten in der WSUS-Datenbank und schlussendlich auch die Contentdaten auf dem WSUS-Server gespeichert. Aufgrund eines 1,1 TB großen WSUS-Contents und einer aufgeblähten Datenbank (> 7 GB) bei einem Kunden, entwickelte ich ein Skript zur Zurücksetzung aller Updateinformationen. Aus Online-Recherchen, in Zusammenarbeit mit dem Kunden und vielen Tests vor Ort, ist nun das folgende Skript entstanden.

Was tut das Skript

Das Skript verbindet sich unter PowerShell mit der WSUS-Datenbank, setzt ALLE Updatedateien auf ABGELEHNT, ENTFERNT ALLE Updatedateien aus der Datenbank, exportiert die aktiv gesetzten Produkte und Klassifizierungen, deaktiviert die aktiv gesetzten Produkte und Klassifizierungen, um schlussendlich diese wieder zu aktivieren, durch einen erneuten Import. Ohne den zuletzt genannten Schritt, ist zwar die Datenbank und der Content am Ende des Skripts leer, aber die WSUS-Konsole blieb fest der Überzeugung, dass es bei einer neuen, initialen Synchronisierung, bereits auf dem aktuellsten Stand sei. Sprich, leere Datenbank (0 Einträge), aktiv gesetzte Produkte und dennoch 0 neue Updatedateien zum herunterladen gefunden. Deswegen das deaktivieren und aktivieren der Produkte und Klassifizierungen.

Damit die Downstream-, Upstream- und Replikatserver gleichermaßen das Skript anwenden können, werden durch das Skript die Updatequellserverinformationen auf „Microsoft“ zurückgesetzt, um die Produkte und Kategorien bearbeiten zu können. Zuvor werden eventuell vorhandene, abweichende Einstellungen zu den Updatequellserverinformationen (z.B. interne Updateserverpfade und weitere aktiv gesetzte Optionen) eingesammelt und gespeichert, um nach Abschluss aller Maßnahmen, die Updatequellserverinformationen wiederherzustellen.

Nach dem entfernen aller Updatedateiinformationen aus der Datenbank, empfiehlt es sich, den Datenbankindex zu aktualisieren, die Serverbereinigung zu starten und die Datenbankgröße zu verkleinern. All diese Maßnahmen habe ich in einer separaten Windows-Aufgabe hinterlegt und führe die Aufgabe 1x täglich aus! Deshalb wird hier im Skript die hinterlegte Windows-Aufgabe „WSUS-Cleanup“ außer der Reihe aufgerufen und gestartet. Diese weiterführenden Maßnahmen habe ich hier im BLOG bereits in anderen Beiträgen beschrieben und diese können gerne übernommen werden. Das Ergebnis ist eine kleine, aber bereinigte Datenbank (~400 MB) und eine Contentspeichergröße von 0 Byte.

Zum Abschluss initialisiert das Skript die WSUS-Synchronisation, damit anhand der aktiv gesetzten Produkte- und Klassifizierungen, die zutreffenden Updatedateien erkannt und neu heruntergeladen werden können.

Ziel

Das Ziel soll es sein, hier einen Weg aufzuzeigen, wie ohne einer Re-Installation der WSUS-Rolle, die Datenbank und schlussendlich der Content erfolgreich auf NULL zurückgesetzt werden können.

Hinweis:

Das Skript erstellt ein entsprechendes LOG-Verzeichnis und hinterlegt dort alle Informationen zu den Vorgängen der Zurücksetzung.


Vorbereitungen

  • lokale Sitzung auf dem WSUS-Server
  • administrativ geöffnete PowerShell ISE
  • PowerShell-Skript-Beispiel kopieren und einfügen
  • Skript-Anpassung: $LogPath
  • Skript-Anpassung: $TaskPath
  • Skript-Anpassung: $TaskName
  • ggf. Skript-Anpassung: [Boolean]$UseSSL = $True oder $False
  • ggf. Skript-Anpassung: [Int32]$PortNumber = 8531 oder 8530

Skript ausführen

Bevor das Skript gestartet werden kann, ist jetzt die Chance, die aktiv gesetzten Produkte und Klassifizierungen an die neuen Gegebenheiten anzupassen! Da sonst die alten Werte übernommen werden und dadurch wieder die falschen Updatedateien durch die WSUS-Synchronisierung geladen werden…

PowerShell-Skript-Beispiel:

<#
.SYNOPSIS
  WSUS-RESET, set Updatefiles in WID-Database and Contentstorage to NULL.
  
.DESCRIPTION
  The script reset the WSUS-Database and Content to NULL.
  All Update informations are removed, after to proceed this script.

.COMPONENT
  Requires Module UpdateServices
  
.OUTPUTS
  Live output on screen.
  Log- and Configfiles under $LogPath.
  Empty WID-Database and Content.
  
.NOTES
  Version:        1.0
  Author:         André Stuhr
  Creation Date:  11/01/2021
  Purpose/Change: First initial script development
#>

Clear-Host

#----------------------------------------
# Load Timestamp Function
function Get-TimeStamp
{
    return "[{0:yyyy-MM-dd} {0:HH:mm:ss}]" -f (Get-Date)
}

#----------------------------------------
# Variables
$LogPath       = "X:\_LOG\WSUSReset"
$TaskPath      = "\WSUS\" 
$TaskName      = "WSUS-Cleanup"
$WsusResetLog  = "$LogPath\WsusResetLog.log"
$WsusDenyLog   = "$LogPath\WsusDenyLog.log"
$WsusDeleteLog = "$LogPath\WsusDeleteLog.log"
$expProd       = "$LogPath\products.csv"
$expCat        = "$LogPath\categories.csv"

#----------------------------------------
# Check Log-Path, and if not exist, then create new Directory
If (!(Test-Path $LogPath))
{
    New-Item -ItemType Directory -Force -Path $LogPath | Out-Null
    
    Write-Host "LOG-VERZEICHNIS: Erstellt" -ForegroundColor "Green"
    Write-Output "$(Get-TimeStamp) LOG-VERZEICHNIS: $LogPath erstellt" | Out-File $WsusResetLog -Append
}

#----------------------------------------
# Connection informationen
[String]$WsusServer = [System.Net.Dns]::GetHostByName($env:computerName).HostName
[Boolean]$UseSSL    = $True
[Int32]$PortNumber  = 8531

#----------------------------------------
# Load .NET assembly
[void][System.Reflection.Assembly]::LoadWithPartialName("Microsoft.UpdateServices.Administration")

#----------------------------------------
# Connect to WSUS Server
$IPAddress = (Get-NetIPAddress -CimSession $WsusServer -AddressFamily IPv4 | where {$_.InterfaceAlias -notmatch 'Loopback'}).IPAddress
$wsus = [Microsoft.UpdateServices.Administration.AdminProxy]::GetUpdateServer($WsusServer,$UseSSL,$PortNumber)

Write-Host "Verbindung zum $WsusServer ($IPAddress) hergestellt" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) Verbindung zum $WsusServer ($IPAddress) hergestellt" | Out-File $WsusResetLog -Append

#----------------------------------------
# Get Synchronization Process
$SyncStatus = $wsus.GetSubscription().GetSynchronizationStatus()
if ($SyncStatus -eq 'Running')
{
    # Stop the WSUS-Synchronization process
    $wsus.GetSubscription().StopSynchronization()

    Write-Host "SYNCHRONISATION: Prozess gestoppt" -ForegroundColor "Yellow"
    Write-Output "$(Get-TimeStamp) SYNCHRONISATION: Prozess gestoppt" | Out-File $WsusResetLog -Append
}
else
{
    Write-Host "SYNCHRONISATION: Prozess inaktiv" -ForegroundColor "Green"
    Write-Output "$(Get-TimeStamp) SYNCHRONISATION: Prozess inaktiv" | Out-File $WsusResetLog -Append
}

#----------------------------------------
# Set to Microsoft Update Server
$ReadUpdateServer = $wsus.GetConfiguration().SyncFromMicrosoftUpdate
if ($ReadUpdateServer -eq $False)
{
    # Read current Values
    [String]$UpstreamWsusServerName      = $wsus.GetConfiguration().UpstreamWsusServerName
    [Int32]$UpstreamWsusServerPortNumber = $wsus.GetConfiguration().UpstreamWsusServerPortNumber
    [Boolean]$UpstreamWsusServerUseSsl   = $wsus.GetConfiguration().UpstreamWsusServerUseSsl
    [Boolean]$IsReplicaServer            = $wsus.GetConfiguration().IsReplicaServer
    
    # Set to Microsoft Update Server
    $wsus | Set-WsusServerSynchronization -SyncFromMU | Out-Null

    Write-Host "UPDATEQUELLE: nach Microsoft geändert" -ForegroundColor "Yellow"
    Write-Output "$(Get-TimeStamp) UPDATEQUELLE: nach Microsoft geändert" | Out-File $WsusResetLog -Append
}
else
{
    Write-Host "UPDATEQUELLE ÄNDERN: Keine Änderung erforderlich!" -ForegroundColor "Green"
    Write-Output "$(Get-TimeStamp) UPDATEQUELLE ÄNDERN: Keine Änderung erforderlich!" | Out-File $WsusResetLog -Append
}

#----------------------------------------
# Define Windows Update Scope
$updatescope = New-Object Microsoft.UpdateServices.Administration.UpdateScope
$u=$wsus.GetUpdates($updatescope)

Write-Host "UPDATEDATEIEN ABLEHNEN: Gestartet" -ForegroundColor "Yellow"
Write-Output "$(Get-TimeStamp) UPDATEDATEIEN ABLEHNEN: Gestartet" | Out-File $WsusResetLog -Append

# Process for each Windows Updatefile, which is not Declined
foreach ($u1 in $u)
{
    if (-not $u1.IsDeclined -eq $true)
    {
        Write-Host ABGELEHNT: $u1.Title
        Write-Output $(Get-TimeStamp) ABGELEHNT: $u1.Title | Out-File $WsusDenyLog -Append
        $u1.Decline()
    }
}

Write-Host "UPDATEDATEIEN ABGELEHNT: Abgeschlossen" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) UPDATEDATEIEN ABGELEHNT: Abgeschlossen" | Out-File $WsusResetLog -Append

#----------------------------------------
# Delete the Updatefiles of all Categories
Write-Host "UPDATEDATEIEN ENTFERNEN: Gestartet" -ForegroundColor "Yellow"
Write-Output "$(Get-TimeStamp) UPDATEDATEIEN ENTFERNEN: Gestartet" | Out-File $WsusResetLog -Append

$wsus.GetUpdates() |
    Where {$_.UpdateClassificationTitle -like "*"} | 
    ForEach-Object `
    {
        $wsus.DeleteUpdate($_.Id.UpdateID);Write-Host ENTFERNT: $_.Title
        Write-Output $(Get-TimeStamp) ENTFERNT: $_.Title | Out-File $WsusDeleteLog -Append
    }

    Write-Host "UPDATEDATEIEN ENTFERNT: Abgeschlossen" -ForegroundColor "Green"
    Write-Output "$(Get-TimeStamp) UPDATEDATEIEN ENTFERNT: Abgeschlossen" | Out-File $WsusResetLog -Append

#----------------------------------------
# Export all current and selected Products
$wsus.GetSubscription().GetUpdateCategories() | select Title, ID | Export-Csv $expProd -Encoding UTF8 -UseCulture -NoTypeInformation

Write-Host "PRODUKT-EXPORT: Abgeschlossen" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) PRODUKT-EXPORT: $expProd" | Out-File $WsusResetLog -Append

#----------------------------------------
# Disable all un- and selected Products
$wsus | Get-WsusProduct | where {$_.TitleIncludes -like "*"} | Set-WsusProduct -Disable

Write-Host "PRODUKTE-DEAKTIVIERT: Abgeschlossen" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) PRODUKTE-DEAKTIVIERT: Abgeschlossen" | Out-File $WsusResetLog -Append

#----------------------------------------
# Import/Enable all exported, selected Products
Write-Host "WIEDERHERSTELLUNG: Produkt-Import gestartet" -ForegroundColor "Yellow"
Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG: Produkt-Import gestartet" | Out-File $WsusResetLog -Append

$csvProduct = Import-Csv -Path $expProd -UseCulture
$csvData    = foreach($product in $csvProduct)
{
    $wsus | Get-WsusProduct | Where-Object {$_.Product.Id -eq $product.Id} | Set-WsusProduct
    
    Write-Host  WIEDERHERSTELLUNG: $product.Title
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG: $product.Title" | Out-File $WsusResetLog -Append
}

Write-Host "WIEDERHERSTELLUNG: Produkt-Import abgeschlossen" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG: Produkt-Import abgeschlossen" | Out-File $WsusResetLog -Append

#----------------------------------------
# Get new selected Products
$wsus.GetSubscription().GetUpdateCategories() | select Title, Id | Out-GridView

#----------------------------------------
# Export all current and selected Categories
$wsus.GetSubscription().GetUpdateClassifications() | select Title, Id | Export-Csv $expCat -Encoding UTF8 -UseCulture -NoTypeInformation

Write-Host "Kategorien-EXPORT: Abgeschlossen" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) Kategorien-EXPORT: $expCat" | Out-File $WsusResetLog -Append

#----------------------------------------
# Disable all un- and selected Categories
$wsus | Get-WsusClassification | Where-Object -FilterScript {$_.Classification.Title -like "*"} | Set-WsusClassification -Disable

Write-Host "Kategorien-DEAKTIVIERT: Abgeschlossen" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) Kategorien-DEAKTIVIERT: Abgeschlossen" | Out-File $WsusResetLog -Append

#----------------------------------------
# Import/Enable all exported, selected Categories
Write-Host "WIEDERHERSTELLUNG: Kategorien-Import gestartet" -ForegroundColor "Yellow"
Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG: Kategorien-Import gestartet" | Out-File $WsusResetLog -Append

$csvCategories = Import-Csv -Path $expCat -UseCulture
$csvData    = foreach($category in $csvCategories)
{
    $wsus | Get-WsusClassification | Where-Object -FilterScript {$_.Classification.Id -eq $category.Id} | Set-WsusClassification
    
    Write-Host  WIEDERHERSTELLUNG: $category.Title
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG: $category.Title" | Out-File $WsusResetLog -Append
}

Write-Host "WIEDERHERSTELLUNG: Kategorien-Import abgeschlossen" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG: Kategorien-Import abgeschlossen" | Out-File $WsusResetLog -Append

#----------------------------------------
# Get new selected Categories
$wsus.GetSubscription().GetUpdateClassifications() | select Title, Id | Out-GridView

#----------------------------------------
# Restore Upstreamsource Settings
$UpdateServerConfig = @{UssServerName=$UpstreamWsusServerName;PortNumber=$UpstreamWsusServerPortNumber}

if ($ReadUpdateServer -eq $True) 
{ 
    Write-Host "WIEDERHERSTELLUNG: Updatequelle Microsoft (ursprüngliche Konfiguration)" -ForegroundColor "Green"
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG: Updatequelle Microsoft (ursprüngliche Konfiguration)" | Out-File $WsusResetLog -Append 
}
elseif ($UpstreamWsusServerUseSsl -eq $true -and $IsReplicaServer -eq $true) 
{ 
    $wsus | Set-WsusServerSynchronization @UpdateServerConfig -UseSsl -Replica | Out-Null

    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" -ForegroundColor "Yellow"
    Write-Host "WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName"
    Write-Host "WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber"
    Write-Host "WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl"
    Write-Host "WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer"
    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" -ForegroundColor "Green"

    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" | Out-File $WsusResetLog -Append
}
elseif ($UpstreamWsusServerUseSsl -eq $true -and $IsReplicaServer -eq $false) 
{ 
    $wsus | Set-WsusServerSynchronization @UpdateServerConfig -UseSsl | Out-Null 

    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" -ForegroundColor "Yellow"
    Write-Host "WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName"
    Write-Host "WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber"
    Write-Host "WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl"
    Write-Host "WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer"
    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" -ForegroundColor "Green"

    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" | Out-File $WsusResetLog -Append
}
elseif ($UpstreamWsusServerUseSsl -eq $false -and $IsReplicaServer -eq $true) 
{ 
    $wsus | Set-WsusServerSynchronization @UpdateServerConfig -Replica | Out-Null 

    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" -ForegroundColor "Yellow"
    Write-Host "WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName"
    Write-Host "WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber"
    Write-Host "WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl"
    Write-Host "WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer"
    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" -ForegroundColor "Green"

    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" | Out-File $WsusResetLog -Append
}
else 
{
    $wsus | Set-WsusServerSynchronization @UpdateServerConfig | Out-Null
        
    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" -ForegroundColor "Yellow"
    Write-Host "WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName"
    Write-Host "WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber"
    Write-Host "WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl"
    Write-Host "WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer"
    Write-Host "WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" -ForegroundColor "Green"

    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen gestartet" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SERVERNAME: $UpstreamWsusServerName" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-PORT:       $UpstreamWsusServerPortNumber" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-SSL:        $UpstreamWsusServerUseSsl" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG-REPLIKAT:   $IsReplicaServer" | Out-File $WsusResetLog -Append
    Write-Output "$(Get-TimeStamp) WIEDERHERSTELLUNG:            Updateserver Synchronisationseinstellungen abgeschlossen" | Out-File $WsusResetLog -Append
}

#----------------------------------------
# Start the WSUS-Cleanup ScheduleTask
Start-ScheduledTask -CimSession $WsusServer -TaskPath $TaskPath -TaskName $TaskName

Write-Host "WSUS-BEREINIGUNGSPROZESS: Wsus-Cleanup gestartet (Aufgabenplanung)" -ForegroundColor "Yellow"
Write-Output "$(Get-TimeStamp) WSUS-BEREINIGUNGSPROZESS: Wsus-Cleanup gestartet (Aufgabenplanung)" | Out-File $WsusResetLog -Append

#----------------------------------------
# Check TaskSchedule State before go further
while (Get-ScheduledTask -CimSession $WsusServer -TaskPath $TaskPath -TaskName $TaskName | where {$_.State -ne "Ready"})
{
    Write-Host (Get-Date) -ForegroundColor "Cyan"
    Write-Host "STATUS: Bereinigungsprozess..." -ForegroundColor "Cyan"
    Write-Host "STATUS: Aktualisierung in 20 Sekunden" -ForegroundColor "Cyan"
    
    Start-Sleep -Seconds 20
    cls
}

Write-Host "WSUS-BEREINIGUNGSPROZESS: abgeschlossen!" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) WSUS-BEREINIGUNGSPROZESS: abgeschlossen!" | Out-File $WsusResetLog -Append

#----------------------------------------
# Start the initial WSUS-Synchronization process
$wsus.GetSubscription().StartSynchronization()

Write-Host "INITIAL-SYNCHRONISATION: gestartet!" -ForegroundColor "Yellow"
Write-Output "$(Get-TimeStamp) INITIAL-SYNCHRONISATION: gestartet!" | Out-File $WsusResetLog -Append

#----------------------------------------
# Check, if the initiale Synchronisation is Done
while ($wsus.GetSubscription().GetSynchronizationStatus() -ne "NotProcessing")
{
    Write-Host (Get-Date) -ForegroundColor "Cyan"
    Write-Host "STATUS: Initial-Synchronisation aktuell in Prozess..." -ForegroundColor "Cyan"
    Write-Host "STATUS: Aktualisierung in 5 Minuten" -ForegroundColor "Cyan"
    
    Start-Sleep -Seconds 300
    cls
}

Write-Host "INITIAL-SYNCHRONISATION: abgeschlossen!" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) INITIAL-SYNCHRONISATION: abgeschlossen!" | Out-File $WsusResetLog -Append

#----------------------------------------
Write-Host "ENDE: WSUS Komplettbereinigung" -ForegroundColor "Green"
Write-Output "$(Get-TimeStamp) ENDE: WSUS Komplettbereinigung" | Out-File $WsusResetLog -Append

Skriptausgabe

Das Skriptbeispiel gibt in der Ausführung den aktuellen Bearbeitungsstand und die entsprechenden Informationen in Echtzeit aus (siehe die folgenden Screenshots).

Produkt-Kontrolle

Bild 8 von 15

Zur Kontrolle erscheint automatisch ein neues Fenster, dass die neu gesetzten Produkte nochmals anzeigt. Da das Skript im Hintergrund automatisch weiter abläuft.

Achtung:

Handelt es sich um einen WSUS-Server, der nicht direkt die Windows Updates von Microsoft bezieht, dann kann es unter ganz bestimmten Umständen dazu kommen, dass die erneute, initiale Synchronisierung kurz nach dem Start mit einer Erfolgsmeldung den Vorgang beendet. Sprich, das zurückgesetzte WSUS-System ist der Meinung, dass es keine neuen, verfügbaren Windows Updates herunterzuladen gibt!

Lösung:

Auf dem übergeordnetem WSUS-System unter "Downstreamserver", dass zurückgesetzte WSUS-System manuell auswählen und löschen! Anschließend den Synchronisationsvorgang auf dem zurückgesetzten WSUS-System manuell anstoßen und durchlaufen lassen.

Das Erarbeiten und die Entwicklung dieses Skripts hat sehr viel Zeit in Anspruch genommen und war nicht immer ganz leicht. Vor allem, da die gut gemeinten Befehle aus dem TechNet, nicht immer funktionierten bzw. funktionieren. Daher freue ich mich stets über eine Rückmeldung, ob das Skript nun auch in anderen Umgebungen erfolgreich zum Einsatz gekommen ist oder ob es hier noch weitere Stolpersteine zu geben scheint… Das Skript ist eigentlich so entwickelt, dass es generell überall eingesetzt werden kann, bis auf ein paar wenige Änderungen, wie eingangs unter den Vorbereitungen erwähnt. Gerne nehme ich auch weitere, sinnvolle Codezeilen mit auf, sollten diese mir genannt und von mir erneut validiert worden sein!

VIEL ERFOLG!


5 thoughts on “WSUS-Server Reset durchführen (zurücksetzen)”

  1. Hallo. Ich probiere dieses Script um unseren WSUS zu bereinigen. Allerdings läuft es nun seit 24h und es sind bisher allein ca. 22.000 „Nvidia Driver …“ entfernt worden. Das Delete-Log selbst umfasst inzwischen 150.000 Zeilen. Also ca. 30.000 Einträge. Erscheint mir dann doch unplausibel.
    Ja, wir hatten „Treiber“ mal für ein paar Tage eingeschaltet, aber wieder deaktiviert.
    Dennoch ist die Anzahl sehr hoch, hingegen die Dateianzahl im WSUS Content allerdings nicht weniger wird. Würde mich über einen Hinweis freuen. Herzlichen Gruß.

    1. Moin Simon,

      initial kann das Skript tatsächlich sehr lange benötigen. Je nachdem, wie viel Treiber Informationen aufgelaufen sind über die Jahre oder halt auch nur bei einem initialen Sync. Der WSUS schmeißt nichts selber weg und muss daher dazu gezwungen werden!

      Bei einem Kunden musste ich einst 1,3 TB Treiber Dateien ablehnen und entfernen. Das hat 1,5 Tage gedauert… daher ist deine aktuelle Dauer noch im Zeitrahmen. 😉

      Bitte beachte noch die ähnlichen Beiträge zum Schluss des Artikels!

      Die lasse ich alle wie hier im Skript zu sehen ist, in der Aufgabenplanung ablaufen:
      Prio 1 – https://www.sit-administration.de/wsus-synchronisierungen-entfernen-susdb/ (wsus_sync.cmd)
      Prio 2 – https://www.sit-administration.de/wsus-serverbereinigung/ (wsus_cleanup.ps1)
      Prio 3 – https://www.sit-administration.de/wsus-datenbankindex-neu-erstellen-defragmentieren-susdb/ (wsus_index.cmd)
      Prio 4 – https://www.sit-administration.de/wsus-datenbankgroesse-susdb-verkleinern/ (wsus_dbshrink.cmd)

      Das Skript hier ist aus einem Projekt heraus entstanden und nutzt daher die hier verwendeten Bausteine, um einen kompletten WSUS-RESET durchführen zu können.

      Ich hoffe das hilft, ansonsten melde Dich! 🙂

      Grüße, André

  2. Hallo André,
    danke erstmal für das umfängliche Script. Da ich mich nächstest Wochenende dran setzen will, den WSUS bei uns zu resetten, hab ich nur eine kurze Frage:
    $TaskPath = „\WSUS\“ – ist hier das Installationsverzeichnis des WSUS gemeint oder der Speicherort des WSUSContent
    Wir haben den WSUSContent Ordner auf eine andere Festplatte verschoben gehab, da dieser zu groß geworden ist.
    Über eine kurze Rückmeldung wäre ich Dir dankbar.
    Viele Grüße,
    Ines

    1. Grüß Dich Ines,

      $TaskPath betrifft das folgende Code-Schnipsel:

      # Start the WSUS-Cleanup ScheduleTask
      Start-ScheduledTask -CimSession $WsusServer -TaskPath $TaskPath -TaskName $TaskName
      Write-Host „WSUS-BEREINIGUNGSPROZESS: Wsus-Cleanup gestartet (Aufgabenplanung)“ -ForegroundColor „Yellow“
      Write-Output „$(Get-TimeStamp) WSUS-BEREINIGUNGSPROZESS: Wsus-Cleanup gestartet (Aufgabenplanung)“ | Out-File $WsusResetLog -Append
      #—————————————-
      # Check TaskSchedule State before go further
      while (Get-ScheduledTask -CimSession $WsusServer -TaskPath $TaskPath -TaskName $TaskName | where {$_.State -ne „Ready“})
      {
      Write-Host (Get-Date) -ForegroundColor „Cyan“
      Write-Host „STATUS: Bereinigungsprozess…“ -ForegroundColor „Cyan“
      Write-Host „STATUS: Aktualisierung in 20 Sekunden“ -ForegroundColor „Cyan“

      Start-Sleep -Seconds 20
      cls
      }
      Write-Host „WSUS-BEREINIGUNGSPROZESS: abgeschlossen!“ -ForegroundColor „Green“
      Write-Output „$(Get-TimeStamp) WSUS-BEREINIGUNGSPROZESS: abgeschlossen!“ | Out-File $WsusResetLog -Append

      Ich habe andere „Aktionen der Serveroptimierung“ in den folgenden Artikeln beschrieben und das alles in einer einzigen Aufgabe zusammengefasst (Wsus-Cleanup):

      Prio 1 – https://www.sit-administration.de/wsus-synchronisierungen-entfernen-susdb/ (wsus_sync.cmd)
      Prio 2 – https://www.sit-administration.de/wsus-serverbereinigung/ (wsus_cleanup.ps1)
      Prio 3 – https://www.sit-administration.de/wsus-datenbankindex-neu-erstellen-defragmentieren-susdb/ (wsus_index.cmd)
      Prio 4 – https://www.sit-administration.de/wsus-datenbankgroesse-susdb-verkleinern/ (wsus_dbshrink.cmd)

      $TaskPath = „\WSUS\“ (manuell erstellter Ordner in der Windows-Aufgabenplanung)
      $TaskName = „WSUS-Cleanup“ (manuell erstellte Aufgabe)

      Alternativ musst Du den WSUS-Cleanup Vorgang im gesamten Skript ausklammern. Die Prio 2 ist eigentlich für das Zurücksetzen entscheidend und kann alleine als Aufgabe ausgeführt werden (oder direkt über wsus_cleanup.ps1 im Code hinterlegen).

      Die anderen Prios können auch manuell im Nachgang gestartet werden. Aber die Empfehlung ist tatsächlich, eine Aufgabe auf dem WSUS Server anzulegen, dass alle vier Prios entsprechend beinhaltet und abarbeitet.

      Ich hoffe, damit ist es nun ein wenig klarer geworden?!
      Ansonsten kannst Du mich auch gerne hierzu direkt kontaktieren (E-Mail oder Telefon).

      Viele Grüße,
      André

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert

Time limit is exhausted. Please reload CAPTCHA.