diff --git a/Examples/Example-33-CleanupPrivateDFSR.ps1 b/Examples/Example-33-CleanupPrivateDFSR.ps1 index 6ccd88d..04b044a 100644 --- a/Examples/Example-33-CleanupPrivateDFSR.ps1 +++ b/Examples/Example-33-CleanupPrivateDFSR.ps1 @@ -4,7 +4,7 @@ Import-Module "$PSScriptRoot\..\GPoZaurr.psd1" -Force # Get dfsr information $DFSR = Get-GPOZaurrSysvolDFSR -$DFSR | Format-Table +$DFSR | Format-Table * # Cleanup DFSR Conflict Path Clear-GPOZaurrSysvolDFSR -WhatIf \ No newline at end of file diff --git a/Public/Clear-GPOZaurrSysvolDFSR.ps1 b/Public/Clear-GPOZaurrSysvolDFSR.ps1 index 439c581..6f73ec5 100644 --- a/Public/Clear-GPOZaurrSysvolDFSR.ps1 +++ b/Public/Clear-GPOZaurrSysvolDFSR.ps1 @@ -3,8 +3,12 @@ function Clear-GPOZaurrSysvolDFSR { param( [alias('ForestName')][string] $Forest, [string[]] $ExcludeDomains, + [string[]] $ExcludeDomainControllers, [alias('Domain', 'Domains')][string[]] $IncludeDomains, - [System.Collections.IDictionary] $ExtendedForestInformation + [alias('DomainControllers')][string[]] $IncludeDomainControllers, + [switch] $SkipRODC, + [System.Collections.IDictionary] $ExtendedForestInformation, + [int] $LimitProcessing = [int32]::MaxValue ) # Based on https://techcommunity.microsoft.com/t5/ask-the-directory-services-team/manually-clearing-the-conflictanddeleted-folder-in-dfsr/ba-p/395711 $StatusCodes = @{ @@ -21,12 +25,17 @@ function Clear-GPOZaurrSysvolDFSR { #WMIC.EXE /namespace:\\root\microsoftdfs path dfsrreplicatedfolderinfo where "replicatedfolderguid='70bebd41-d5ae-4524-b7df-4eadb89e511e'" call cleanupconflictdirectory # https://docs.microsoft.com/en-us/previous-versions/windows/desktop/dfsr/dfsrreplicatedfolderinfo - $ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation - foreach ($Domain in $ForestInformation.Domains) { - Write-Verbose "Clear-GPOZaurrSysvolDFSR - Processing $Domain" - $QueryServer = $ForestInformation['QueryServers']["$Domain"].HostName[0] - $DFSR = Get-GPOZaurrSysvolDFSR -IncludeDomains $Domain -ExtendedForestInformation $ForestInformation - $Executed = Invoke-CimMethod -InputObject $DFSR.DFSR -MethodName 'cleanupconflictdirectory' -CimSession $QueryServer + $getGPOZaurrSysvolDFSRSplat = @{ + Forest = $Forest + IncludeDomains = $IncludeDomains + ExcludeDomains = $ExcludeDomains + ExtendedForestInformation = $ExtendedForestInformation + ExcludeDomainControllers = $ExcludeDomainControllers + IncludeDomainControllers = $IncludeDomainControllers + SkipRODC = $SkipRODC + } + Get-GPOZaurrSysvolDFSR @getGPOZaurrSysvolDFSRSplat | Select-Object -First $LimitProcessing | ForEach-Object { + $Executed = Invoke-CimMethod -InputObject $_.DFSR -MethodName 'cleanupconflictdirectory' -CimSession $_.ComputerName if ($Executed) { [PSCustomObject] @{ Status = $StatusCodes["$($Executed.ReturnValue)"] diff --git a/Public/Get-GPOZaurrSysvolDFSR.ps1 b/Public/Get-GPOZaurrSysvolDFSR.ps1 index e7db0a4..027c3f8 100644 --- a/Public/Get-GPOZaurrSysvolDFSR.ps1 +++ b/Public/Get-GPOZaurrSysvolDFSR.ps1 @@ -3,31 +3,38 @@ function Get-GPOZaurrSysvolDFSR { param( [alias('ForestName')][string] $Forest, [string[]] $ExcludeDomains, + [string[]] $ExcludeDomainControllers, [alias('Domain', 'Domains')][string[]] $IncludeDomains, + [alias('DomainControllers')][string[]] $IncludeDomainControllers, + [switch] $SkipRODC, [System.Collections.IDictionary] $ExtendedForestInformation, [string] $SearchDFSR = 'SYSVOL Share' ) - $ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation + $ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExcludeDomainControllers $ExcludeDomainControllers -IncludeDomainControllers $IncludeDomainControllers -SkipRODC:$SkipRODC -ExtendedForestInformation $ExtendedForestInformation foreach ($Domain in $ForestInformation.Domains) { Write-Verbose "Get-GPOZaurrSysvolDFSR - Processing $Domain" - $QueryServer = $ForestInformation['QueryServers']["$Domain"].HostName[0] - - $DFSRConfig = Get-CimInstance -Namespace 'root\microsoftdfs' -Class 'dfsrreplicatedfolderconfig' -ComputerName $QueryServer | Where-Object { $_.ReplicatedFolderName -eq $SearchDFSR } - $DFSR = Get-CimInstance -Namespace 'root\microsoftdfs' -Class 'dfsrreplicatedfolderinfo' -ComputerName $QueryServer | Where-Object { $_.ReplicatedFolderName -eq $SearchDFSR } - if ($DFSR -and $DFSRConfig -and ($DFSR.ReplicatedFolderGuid -eq $DFSRConfig.ReplicatedFolderGuid)) { - [PSCustomObject] @{ - ComputerName = $DFSR.PSComputerName - DomainName = $Domain - ConflictPath = $DFSRConfig.ConflictPath - LastConflictCleanupTime = $DFSR.LastConflictCleanupTime - CurrentConflictSizeInMb = $DFSR.CurrentConflictSizeInMb - MaximumConflictSizeInMb = $DFSRConfig.ConflictSizeInMb - LastErrorCode = $DFSR.LastErrorCode - LastErrorMessageId = $DFSR.LastErrorMessageId - LastTombstoneCleanupTime = $DFSR.LastTombstoneCleanupTime - ReplicatedFolderGuid = $DFSR.ReplicatedFolderGuid - DFSRConfig = $DFSRConfig - DFSR = $DFSR + foreach ($DC in $ForestInformation.DomainDomainControllers[$Domain]) { + Write-Verbose "Get-GPOZaurrSysvolDFSR - Processing $Domain \ $($DC.HostName)" + #$QueryServer = $ForestInformation['QueryServers']["$Domain"].HostName[0] + $DFSRConfig = Get-CimInstance -Namespace 'root\microsoftdfs' -Class 'dfsrreplicatedfolderconfig' -ComputerName $($DC.HostName) | Where-Object { $_.ReplicatedFolderName -eq $SearchDFSR } + $DFSR = Get-CimInstance -Namespace 'root\microsoftdfs' -Class 'dfsrreplicatedfolderinfo' -ComputerName $($DC.HostName) | Where-Object { $_.ReplicatedFolderName -eq $SearchDFSR } + if ($DFSR -and $DFSRConfig -and ($DFSR.ReplicatedFolderGuid -eq $DFSRConfig.ReplicatedFolderGuid)) { + [PSCustomObject] @{ + ComputerName = $DFSR.PSComputerName + DomainName = $Domain + ConflictPath = $DFSRConfig.ConflictPath + LastConflictCleanupTime = $DFSR.LastConflictCleanupTime + CurrentConflictSizeInMb = $DFSR.CurrentConflictSizeInMb + MaximumConflictSizeInMb = $DFSRConfig.ConflictSizeInMb + LastErrorCode = $DFSR.LastErrorCode + LastErrorMessageId = $DFSR.LastErrorMessageId + LastTombstoneCleanupTime = $DFSR.LastTombstoneCleanupTime + ReplicatedFolderGuid = $DFSR.ReplicatedFolderGuid + DFSRConfig = $DFSRConfig + DFSR = $DFSR + } + } else { + Write-Warning "Get-GPOZaurrSysvolDFSR - Couldn't process $($DC.HostName). Conditions not met." } } }