I decided to spend some of the quiet time now at the beginning of the new year to clean up Group Policy here at my new job. We had roughly the same number of GPOs as staff!
I’d already removed at least 10-20 GPOs manually, but I wanted a quick way to find all of the un-linked GPOs that were still just sitting around.
I found this great post by Mark Schill from back in 2013 that still does the job.
Mark’s solution, however, pulls out only the display name property. I needed to modify his solution a little, as I wanted to pipe the results to the Remove-GPO cmdlet. Here’s what I did:
Get-GPO -All | Where-Object { $_ | Get-GPOReport -ReportType XML | Select-String -NotMatch "<LinksTo>" }
The above one-liner gets all unlinked GPOs, and returns Microsoft.GroupPolicy.Gpo objects.
It goes without saying that you should be very careful when bulk-deleting anything. I first backed up all of my GPOs and dumped the list into text format to review it. I manually checked the settings on a few of the GPOs in question, and only then, deleted them.
Here’s how I generated the list to review:
$unlinkedGPOs = Get-GPO -All | Where-Object { $_ | Get-GPOReport -ReportType XML | Select-String -NotMatch "<LinksTo>" }
$unlinkedGPOs | Sort-Object -Property DisplayName | Select-Object DisplayName,CreationTime,ModificationTime | Format-Table