Att avinstallera en patch på en windows server är relativt enkelt via ’Add/Remove Programs’ men att avinstallera samtliga installerade windowspatchar kan vara en plåga.
Ett scenario som jag råkat ut för är att en servern strippats på samtliga oanvända roles and features (av mig ska tilläggas. 😉 ).
När man efter patchning ska lägga på en feature som ligger som ’Removed’ så kan det ibland skita sig.
Lösningen jag hittat är att avinstallera alla patchar, lägga till rollen och sen patcha upp systemet igen. Helt kasst, jag vet. 🙂
Nåja, för att att göra livet lite enklare har jag tagit fram nedanstående script för att avinstallera alla windowspatchar som installerats på en Windows Server. I mitt fall var det en Windows Server 2012.
Vi kommer använda oss av Powershell och WMI-objekt för att få fram en aktuell lista på installerade patchar och avinstallera dessa.
Från början i mitt fall fanns det ca 140 patchar installerade. Efter att ha avinstallerat dessa på en gång ville systemet inte riktigt vara med längre. Så, för att lösa det la jag in en batch på 30 patchar åt gången, sen omstart och så 30 till osv…
Nog snackat, här kommer scriptet. Håll till godo. 🙂
[CmdletBinding()]
Param()
# Script för avinstallation av samtliga windowspatchar på en windows server.
# Batch på 30 patchar åt gången, ändra $limit till önskat antal patchar / körning.
# Jag kör med /log på wusa.exe för att logga händelserna. Loggen lagras i samma mapp som scriptet körs från.
# Du kan därefter öpppna loggen i eventloggen.
# Scriptet är verifierat på Windows Server 2012 men bör fungera på övriga Windows-OS också.
# För att köra utan limit. Sätt $limit = -1
$limit = 30
# Ändra inget nedan.
$reachedLimit = 0
$GetPatches = Get-WmiObject Win32_QuickFixEngineering
# Gå igenom listan
foreach ($patch in $GetPatches){
# Kör enbart upp till $limit
if ($reachedLimit -ne $limit){
$reachedLimit++
# Rensa patchen på text så enbart KB-numret är kvar.
$KB = $patch.HotfixId.Replace("KB", "")
$DeletePatchCmd = "wusa.exe /uninstall /kb:$KB /quiet /log /norestart"
Write-Verbose "Raderar patchen med följande kommando: $($DeletePatchCmd)"
Invoke-Expression $DeletePatchCmd
# Kör en loop för att invänta slutförd avinstallation innan nästa patch kan avinstalleras.
while (@(Get-Process wusa -ErrorAction SilentlyContinue).Count -ne 0)
{
Start-Sleep 3
Write-Verbose "Väntar på att patchen avinstalleras..."
}
}
}