# Patching and Deploying Windows Over the Network with Configuration Manager # https://www.zadran.net/guides/patching-and-deploying-windows-with-configuration-manager # Generated from the guide, last updated 2026-10-18. # # NO WARRANTY. This script is provided as is. You are responsible for # understanding what it does before running it, and for the consequences. # Take a backup first. See https://www.zadran.net/disclaimer # # Destructive steps are left commented out on purpose -- uncomment them # only once you have understood what they do. # # If Windows will not run this file: a script saved from a browser is # marked as downloaded, and the RemoteSigned policy (the Windows Server # default) refuses it until you run Unblock-File .\patching-and-deploying-windows-with-configuration-manager.ps1 # Where the policy is Restricted (the Windows 10 and 11 default), run it as # powershell -ExecutionPolicy Bypass -File .\patching-and-deploying-windows-with-configuration-manager.ps1 $ErrorActionPreference = 'Stop' # ---- Set these for your environment ---- # The NetBIOS name of the same server. $SERVERNAME = 'CM01' # The short form of your domain name, used before the backslash in account names. $NETBIOS = 'YOURDOMAIN' # The account you run the Configuration Manager console as. $ADMINUSER = 'admin' Install-WindowsFeature UpdateServices-Services,UpdateServices-DB -IncludeManagementTools cd "C:\Program Files\Update Services\Tools" .\wsusutil.exe postinstall SQL_INSTANCE_NAME="${SERVERNAME}" CONTENT_DIR=E:\WSUS Import-Module WebAdministration Set-ItemProperty 'IIS:\AppPools\WsusPool' -Name recycling.periodicRestart.privateMemory -Value 0 Set-ItemProperty 'IIS:\AppPools\WsusPool' -Name queueLength -Value 2000 Restart-WebAppPool -Name WsusPool New-NetFirewallRule -DisplayName "WSUS HTTP 8530" -Direction Inbound -Protocol TCP -LocalPort 8530 -Action Allow New-NetFirewallRule -DisplayName "WSUS HTTPS 8531" -Direction Inbound -Protocol TCP -LocalPort 8531 -Action Allow & "$env:ProgramFiles\Windows Defender\MpCmdRun.exe" -RemoveDefinitions -All Get-MpComputerStatus | Select-Object AntivirusSignatureVersion Get-GPO -All | ForEach-Object { $r = Get-GPOReport -Guid $_.Id -ReportType Xml if ($r -match 'WUServer|WindowsUpdate') { $_.DisplayName } } Get-ItemProperty 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\WindowsUpdate' | Select-Object WUServer, DoNotConnectToWindowsUpdateInternetLocations, DisableDualScan Get-MpPreference | Select-Object SignatureFallbackOrder Get-WmiObject -Namespace root\ccm\SoftwareUpdates\UpdatesStore -Class CCM_UpdateStatus | Where-Object { $_.Status -eq 'Missing' } | Select-Object Article, Title, Status | Format-Table -AutoSize Get-DnsClientServerAddress -AddressFamily IPv4 | Select-Object InterfaceAlias, ServerAddresses nltest /dsgetdc:yourdomain.com Resolve-DnsName google.com | Select-Object -First 1 Set-ItemProperty "E:\Sources\OSD\Images\Win11\install.wim" -Name IsReadOnly -Value $false Get-WindowsImage -ImagePath "E:\Sources\OSD\Images\Win11\install.wim" | Select-Object ImageIndex, ImageName | Format-Table -AutoSize Dism /Export-Image /SourceImageFile:"E:\Sources\OSD\Images\Win11\install.wim" ` /SourceIndex:6 /DestinationImageFile:"E:\Sources\OSD\Images\Win11-Pro\install.wim" ` /Compress:max /CheckIntegrity $CMLogs = Join-Path (Get-ItemProperty 'HKLM:\SOFTWARE\Microsoft\SMS\Identification')."Installation Directory" 'Logs' Get-ItemProperty 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\WindowsUpdate' | Select-Object WUServer, DoNotConnectToWindowsUpdateInternetLocations, DisableDualScan @(Get-WmiObject -Namespace root\ccm\Policy\Machine\ActualConfig -Class CCM_UpdateCMAssignment).Count Get-WmiObject -Namespace root\ccm\SoftwareUpdates\UpdatesStore -Class CCM_UpdateStatus | Group-Object Status | Select-Object Name, Count ([wmiclass]'root\ccm:SMS_Client').TriggerSchedule('{00000000-0000-0000-0000-000000000021}') # Machine policy ([wmiclass]'root\ccm:SMS_Client').TriggerSchedule('{00000000-0000-0000-0000-000000000113}') # Software update scan ([wmiclass]'root\ccm:SMS_Client').TriggerSchedule('{00000000-0000-0000-0000-000000000108}') # Update deployment evaluation $store = New-Object -ComObject Microsoft.CCM.UpdatesStore $store.RefreshServerComplianceState() Grant-SmbShareAccess -Name 'Sources$' -AccountName "${NETBIOS}\${ADMINUSER}" -AccessRight Change -Force