diff --git a/Examples/Example-01-BackupGPOs.ps1 b/Examples/Example-01-BackupGPOs.ps1 index eb0fe97..3d058ab 100644 --- a/Examples/Example-01-BackupGPOs.ps1 +++ b/Examples/Example-01-BackupGPOs.ps1 @@ -2,7 +2,7 @@ # Backup GPOs $BackupPath = "$Env:UserProfile\Desktop\GPO" -$GPOSummary = Backup-GPOZaurr -BackupPath $BackupPath -Verbose -Type EmptyAndUnlinked -BackupDated #-LimitProcessing 1 +$GPOSummary = Backup-GPOZaurr -BackupPath $BackupPath -Verbose -Type Unlinked -BackupDated #-LimitProcessing 1 $GPOSummary | Format-Table -AutoSize # Confirm GPOs are backed up properly diff --git a/Examples/Example-02-RemoveEmptyAndUnlinkedGPOs.ps1 b/Examples/Example-02-RemoveEmptyAndUnlinkedGPOs.ps1 index 5cb27e3..39dc451 100644 --- a/Examples/Example-02-RemoveEmptyAndUnlinkedGPOs.ps1 +++ b/Examples/Example-02-RemoveEmptyAndUnlinkedGPOs.ps1 @@ -2,4 +2,4 @@ # Remove GPOS $BackupPath = "$Env:UserProfile\Desktop\GPO" -Remove-GPOZaurr -Type EmptyAndUnlinked -BackupPath $BackupPath -BackupDated -LimitProcessing 2 -Verbose \ No newline at end of file +Remove-GPOZaurr -Type Empty -BackupPath $BackupPath -BackupDated -LimitProcessing 2 -Verbose \ No newline at end of file diff --git a/Examples/Example-03-RestoreGPO.ps1 b/Examples/Example-03-RestoreGPO.ps1 index ba730d7..0479f27 100644 --- a/Examples/Example-03-RestoreGPO.ps1 +++ b/Examples/Example-03-RestoreGPO.ps1 @@ -1,6 +1,6 @@ Import-Module "$PSScriptRoot\..\GPoZaurr.psd1" -Force -$RestoreFrom = 'C:\Users\przemyslaw.klys\Desktop\GPO\2020-04-02_20_20_04' +$RestoreFrom = 'C:\Users\przemyslaw.klys\Desktop\GPO\2020-04-12_10_11_24' $BackupInformation = Get-GPOZaurrBackupInformation -BackupFolder $RestoreFrom $BackupInformation | Format-Table -a @@ -10,5 +10,5 @@ $RestoredGPOs = Restore-GPOZaurr -BackupFolder $RestoreFrom -Verbose $RestoredGPOs | Format-Table -AutoSize # restore just one Gpo -$RestoredGPOs = Restore-GPOZaurr -BackupFolder $RestoreFrom -Verbose -DisplayName 'Users | Synced Office 365 Users' -$RestoredGPOs | Format-Table -AutoSize \ No newline at end of file +#$RestoredGPOs = Restore-GPOZaurr -BackupFolder $RestoreFrom -Verbose -DisplayName 'Users | Synced Office 365 Users' +#$RestoredGPOs | Format-Table -AutoSize \ No newline at end of file diff --git a/Examples/Example-07-CreatingWMIFilters.ps1 b/Examples/Example-07-CreatingWMIFilters.ps1 index 4106449..93b9419 100644 --- a/Examples/Example-07-CreatingWMIFilters.ps1 +++ b/Examples/Example-07-CreatingWMIFilters.ps1 @@ -1,7 +1,7 @@ Import-Module "$PSScriptRoot\..\GPoZaurr.psd1" -Force # By default it creates WMI filter in $Env:USERDNSDOMAIN if no Forest/IncludeDomains/ExcludeDomains are specified -New-GPOZaurrWMI -Query 'select * from Win32_OperatingSystem where Version like "6.0%" and ProductType = "3"' -Name 'Test' -Verbose -Force +New-GPOZaurrWMI -Query 'select * from Win32_OperatingSystem where Version like "6.0%" and ProductType = "3"' -Name 'Test' -Verbose #-Force # If you want to force creation of same filter in all domains of a forest (this overwrites set value) #New-GPOZaurrWMI -Query 'select * from Win32_OperatingSystem where Version like "6.0%" and ProductType = "3"' -Name 'Test' -Verbose -Forest 'ad.evotec.xyz' -WhatIf diff --git a/Examples/Example-08-ListingPermissions.ps1 b/Examples/Example-08-ListingPermissions.ps1 index fbdfeb9..3e7d22d 100644 --- a/Examples/Example-08-ListingPermissions.ps1 +++ b/Examples/Example-08-ListingPermissions.ps1 @@ -8,9 +8,10 @@ #$GPOs[0].ACL | Format-Table -AutoSize #Get-GPOZaurrPermissions | Format-Table -AutoSize -$T = Get-GPOZaurrPermissions #| Out-HtmlView +$T = Get-GPOZaurrPermission #| Out-HtmlView #$T[0] | Format-List * $T | Format-Table -AutoSize * #$T[0].Trustee #$T[0].Permission -#$T[0] \ No newline at end of file +#$T[0] +$T | Out-HtmlView -ScrollX -Filtering -Online -DisablePaging \ No newline at end of file diff --git a/Examples/Example-09-RemovingGPOPermission.ps1 b/Examples/Example-09-RemovingGPOPermission.ps1 new file mode 100644 index 0000000..9627b20 --- /dev/null +++ b/Examples/Example-09-RemovingGPOPermission.ps1 @@ -0,0 +1,3 @@ +Import-Module "$PSScriptRoot\..\GPoZaurr.psd1" -Force + +Remove-GPOZaurrPermission -Verbose \ No newline at end of file diff --git a/Examples/Example-10-ReplaceGPOOwner.ps1 b/Examples/Example-10-ReplaceGPOOwner.ps1 new file mode 100644 index 0000000..f08aeba --- /dev/null +++ b/Examples/Example-10-ReplaceGPOOwner.ps1 @@ -0,0 +1,21 @@ +Import-Module "$PSScriptRoot\..\GPoZaurr.psd1" -Force + +$LImitProcessing = 2 + +# check what is there now +$GPOs = Get-GPOZaurr #-GPOName 'New Group Policy Object' +$GPOs | Format-Table DisplayName, Owner, OwnerSID +$Count = 0 + +# loop thru all GPOS (or use LimitProcessing) +foreach ($GPO in $GPOS) { + $Count++ + Set-GPOZaurrOwner -GPOID $GPO.GUID -Verbose -Principal 'przemyslaw.klys@evotec.pl' #-WhatIf + if ($Count -eq $LImitProcessing) { + break + } +} + +# Confirm what changed +$GPOs = Get-GPOZaurr #-GPOName 'New Group Policy Object' +$GPOs | Format-Table DisplayName, Owner, OwnerSID \ No newline at end of file diff --git a/Examples/Example-11-ReplaceGPOOwnerAutomated.ps1 b/Examples/Example-11-ReplaceGPOOwnerAutomated.ps1 new file mode 100644 index 0000000..62add99 --- /dev/null +++ b/Examples/Example-11-ReplaceGPOOwnerAutomated.ps1 @@ -0,0 +1,13 @@ +Import-Module "$PSScriptRoot\..\GPoZaurr.psd1" -Force + +# This Example shows how to deal with GPOs that have owner that doesn't exists anymore (deleted userr or diff domain) - EmptyOrUnknown +# And also can fix at the same time NonAdministrative - this basically looks for users/groups that are not Domain Admins or Enterprise Admins +# regardless if current user is still Domain Admin or not + +$GPOs = Get-GPOZaurr #-GPOName 'New Group Policy Object' +$GPOs | Format-Table DisplayName, Owner, OwnerSID + +Set-GPOZaurrOwner -Type 'NonAdministrative','EmptyOrUnknown' -Verbose -LimitProcessing 3 #-WhatIf + +$GPOs = Get-GPOZaurr #-GPOName 'New Group Policy Object' +$GPOs | Format-Table DisplayName, Owner, OwnerSID \ No newline at end of file diff --git a/Examples/Example-12-GPOInformationPermissionOnly.ps1 b/Examples/Example-12-GPOInformationPermissionOnly.ps1 new file mode 100644 index 0000000..431ac4d --- /dev/null +++ b/Examples/Example-12-GPOInformationPermissionOnly.ps1 @@ -0,0 +1,9 @@ +Import-Module "$PSScriptRoot\..\GPoZaurr.psd1" -Force + +$GPOS = Get-GPOZaurr -PermissionsOnly +# to screen +$GPOS | Format-Table -AutoSize +# to html +#$GPOS | Out-HtmlView +# to excel +#$GPOS | ConvertTo-Excel -FilePath $Env:UserProfile\Desktop\GPOExport.xlsx -ExcelWorkSheetName 'Permissions' -AutoFit -AutoFilter \ No newline at end of file diff --git a/GPOZaurr.psd1 b/GPOZaurr.psd1 index a8e04a9..47f5b3d 100644 --- a/GPOZaurr.psd1 +++ b/GPOZaurr.psd1 @@ -5,7 +5,7 @@ CompatiblePSEditions = 'Desktop' Copyright = '(c) 2011 - 2020 Przemyslaw Klys @ Evotec. All rights reserved.' Description = 'Group Policy Eater' - FunctionsToExport = 'Backup-GPOZaurr', 'Get-GPOZaurr', 'Get-GPOZaurrBackupInformation', 'Get-GPOZaurrPassword', 'Get-GPOZaurrPermissions', 'Get-GPOZaurrWMI', 'New-GPOZaurrWMI', 'Remove-GPOZaurr', 'Remove-GPOZaurrWMI', 'Restore-GPOZaurr', 'Save-GPOZaurrFiles' + FunctionsToExport = 'Backup-GPOZaurr', 'Get-GPOZaurr', 'Get-GPOZaurrBackupInformation', 'Get-GPOZaurrPassword', 'Get-GPOZaurrPermission', 'Get-GPOZaurrWMI', 'New-GPOZaurrWMI', 'Remove-GPOZaurr', 'Remove-GPOZaurrPermission', 'Remove-GPOZaurrWMI', 'Restore-GPOZaurr', 'Save-GPOZaurrFiles', 'Set-GPOZaurrOwner', 'Set-GPOZaurrWMI' GUID = 'f7d4c9e4-0298-4f51-ad77-e8e3febebbde' ModuleVersion = '0.0.9' PowerShellVersion = '5.1' @@ -20,6 +20,10 @@ ModuleVersion = '0.0.134' ModuleName = 'PSSharedGoods' Guid = 'ee272aa8-baaa-4edf-9f45-b6d6f7d844fe' + }, @{ + ModuleVersion = '0.0.47' + ModuleName = 'ADEssentials' + Guid = '9fc9fd61-7f11-4f4b-a527-084086f1905f' }, 'ActiveDirectory', 'GroupPolicy', 'CimCmdlets', 'Microsoft.PowerShell.Management', 'Microsoft.PowerShell.Utility' RootModule = 'GPOZaurr.psm1' } \ No newline at end of file diff --git a/Private/ConvertTo-TableFormat.ps1 b/Private/ConvertTo-TableFormat.ps1 deleted file mode 100644 index ebd64ad..0000000 --- a/Private/ConvertTo-TableFormat.ps1 +++ /dev/null @@ -1,45 +0,0 @@ -function ConvertTo-TableFormat { - <# - .SYNOPSIS - Rebuild an object based on the Format Data for the object. - .DESCRIPTION - Allows an object to be rebuilt based on the view data for the object. Uses Select-Object to create a new PSCustomObject. - #> - [CmdletBinding()] - param ( - [Parameter(ValueFromPipeline)] - [Object]$InputObject - ) - begin { - $isFirst = $true - } - process { - $format = if ($isFirst) { - $formatData = Get-FormatData -TypeName $InputObject.PSTypeNames | Select-Object -First 1 - if ($formatData) { - $viewDefinition = $formatData.FormatViewDefinition | Where-Object Control -match 'TableControl' - - for ($i = 0; $i -lt $viewDefinition.Control.Headers.Count; $i++) { - $name = $viewDefinition.Control.Headers[$i].Label - - $displayEntry = $viewDefinition.Control.Rows.Columns[$i].DisplayEntry - if (-not $name) { - $name = $displayEntry.Value - } - - $expression = switch ($displayEntry.ValueType) { - 'Property' { $displayEntry.Value } - 'ScriptBlock' { [ScriptBlock]::Create($displayEntry.Value) } - } - - @{ Name = $name; Expression = $expression } - } - } - } - if ($format) { - $InputObject | Select-Object -Property $format - } else { - $InputObject - } - } -} \ No newline at end of file diff --git a/Private/Get-ADAdministrativeGroups.ps1 b/Private/Get-ADAdministrativeGroups.ps1 new file mode 100644 index 0000000..6337bd5 --- /dev/null +++ b/Private/Get-ADAdministrativeGroups.ps1 @@ -0,0 +1,71 @@ + +function Get-ADADministrativeGroups { + <# + .SYNOPSIS + Short description + + .DESCRIPTION + Long description + + .PARAMETER Type + Parameter description + + .PARAMETER Forest + Parameter description + + .PARAMETER ExcludeDomains + Parameter description + + .PARAMETER IncludeDomains + Parameter description + + .PARAMETER ExtendedForestInformation + Parameter description + + .EXAMPLE + Get-ADADministrativeGroups -Type DomainAdmins, EnterpriseAdmins + + Output (Where VALUE is Get-ADGroup output): + Name Value + ---- ----- + ByNetBIOS {EVOTEC\Domain Admins, EVOTEC\Enterprise Admins, EVOTECPL\Domain Admins} + ad.evotec.xyz {DomainAdmins, EnterpriseAdmins} + ad.evotec.pl {DomainAdmins} + + .NOTES + General notes + #> + [cmdletBinding()] + param( + [parameter(Mandatory)][validateSet('DomainAdmins', 'EnterpriseAdmins')][string[]] $Type, + [alias('ForestName')][string] $Forest, + [string[]] $ExcludeDomains, + [alias('Domain', 'Domains')][string[]] $IncludeDomains, + [System.Collections.IDictionary] $ExtendedForestInformation + ) + $ADDictionary = [ordered] @{ } + $ADDictionary['ByNetBIOS'] = [ordered] @{ } + + $ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation + foreach ($Domain in $ForestInformation.Domains) { + $ADDictionary[$Domain] = [ordered] @{ } + $QueryServer = $ForestInformation['QueryServers'][$Domain]['HostName'][0] + $DomainInformation = Get-ADDomain -Server $QueryServer + + if ($Type -contains 'DomainAdmins') { + Get-ADGroup -Filter "SID -eq '$($DomainInformation.DomainSID)-512'" -Server $QueryServer -ErrorAction SilentlyContinue | ForEach-Object { + $ADDictionary['ByNetBIOS']["$($DomainInformation.NetBIOSName)\$($_.Name)"] = $_ + $ADDictionary[$Domain]['DomainAdmins'] = "$($DomainInformation.NetBIOSName)\$($_.Name)" + } + } + if ($Type -contains 'EnterpriseAdmins') { + Get-ADGroup -Filter "SID -eq '$($DomainInformation.DomainSID)-519'" -Server $QueryServer -ErrorAction SilentlyContinue | ForEach-Object { + $ADDictionary['ByNetBIOS']["$($DomainInformation.NetBIOSName)\$($_.Name)"] = $_ + $ADDictionary[$Domain]['EnterpriseAdmins'] = "$($DomainInformation.NetBIOSName)\$($_.Name)" + } + } + } + return $ADDictionary +} + +#Get-ADADministrativeGroups -Type DomainAdmins, EnterpriseAdmins \ No newline at end of file diff --git a/Private/Get-XMLGPO.ps1 b/Private/Get-XMLGPO.ps1 index c62a479..718a260 100644 --- a/Private/Get-XMLGPO.ps1 +++ b/Private/Get-XMLGPO.ps1 @@ -2,7 +2,8 @@ [cmdletBinding()] param( [XML] $XMLContent, - [Microsoft.GroupPolicy.Gpo] $GPO + [Microsoft.GroupPolicy.Gpo] $GPO, + [switch] $PermissionsOnly ) if ($XMLContent.GPO.LinksTo) { $Linked = $true @@ -34,63 +35,103 @@ $Enabled = 'User configuration settings disabled' } - [PsCustomObject] @{ - 'Name' = $XMLContent.GPO.Name - 'Domain' = $XMLContent.GPO.Identifier.Domain.'#text' - 'GUID' = $XMLContent.GPO.Identifier.Identifier.InnerText - 'Linked' = $Linked - 'LinksCount' = $LinksCount - 'Enabled' = $Enabled - 'ComputerEnabled' = $ComputerEnabled - 'UserEnabled' = $UserEnabled - 'ComputerSettingsAvailable' = if ($null -eq $XMLContent.GPO.Computer.ExtensionData) { $false } else { $true } - 'UserSettingsAvailable' = if ($null -eq $XMLContent.GPO.User.ExtensionData) { $false } else { $true } - 'ComputerSettingsStatus' = if ($XMLContent.GPO.Computer.VersionDirectory -eq 0 -and $XMLContent.GPO.Computer.VersionSysvol -eq 0) { "NeverModified" } else { "Modified" } - 'ComputerSetttingsVersionIdentical' = if ($XMLContent.GPO.Computer.VersionDirectory -eq $XMLContent.GPO.Computer.VersionSysvol) { $true } else { $false } - 'ComputerSettings' = $XMLContent.GPO.Computer.ExtensionData.Extension - 'UserSettingsStatus' = if ($XMLContent.GPO.User.VersionDirectory -eq 0 -and $XMLContent.GPO.User.VersionSysvol -eq 0) { "NeverModified" } else { "Modified" } - 'UserSettingsVersionIdentical' = if ($XMLContent.GPO.User.VersionDirectory -eq $XMLContent.GPO.User.VersionSysvol) { $true } else { $false } - 'UserSettings' = $XMLContent.GPO.User.ExtensionData.Extension - - 'CreationTime' = [DateTime] $XMLContent.GPO.CreatedTime - 'ModificationTime' = [DateTime] $XMLContent.GPO.ModifiedTime - 'ReadTime' = [DateTime] $XMLContent.GPO.ReadTime - - 'WMIFilter' = $GPO.WmiFilter.name - 'WMIFilterDescription' = $GPO.WmiFilter.Description - 'Path' = $GPO.Path - 'SDDL' = if ($Splitter -ne '') { $XMLContent.GPO.SecurityDescriptor.SDDL.'#text' -join $Splitter } else { $XMLContent.GPO.SecurityDescriptor.SDDL.'#text' } - 'Owner' = $XMLContent.GPO.SecurityDescriptor.Owner.Name.'#text' - 'OwnerSID' = $XMLContent.GPO.SecurityDescriptor.Owner.SID.'#text' - 'ACL' = $XMLContent.GPO.SecurityDescriptor.Permissions.TrusteePermissions | ForEach-Object -Process { + if ($PermissionsOnly) { + [PsCustomObject] @{ + 'DisplayName' = $XMLContent.GPO.Name + 'DomainName' = $XMLContent.GPO.Identifier.Domain.'#text' + 'GUID' = $XMLContent.GPO.Identifier.Identifier.InnerText + 'Enabled' = $Enabled + 'Name' = $XMLContent.GPO.SecurityDescriptor.Owner.Name.'#text' + 'Sid' = $XMLContent.GPO.SecurityDescriptor.Owner.SID.'#text' + #'SidType' = if (($XMLContent.GPO.SecurityDescriptor.Owner.SID.'#text').Length -le 10) { 'WellKnown' } else { 'Other' } + 'PermissionType' = 'Allow' + 'Inherited' = $false + 'Permissions' = 'Owner' + } + $XMLContent.GPO.SecurityDescriptor.Permissions.TrusteePermissions | ForEach-Object -Process { if ($_) { [PsCustomObject] @{ + 'DisplayName' = $XMLContent.GPO.Name + 'DomainName' = $XMLContent.GPO.Identifier.Domain.'#text' + 'GUID' = $XMLContent.GPO.Identifier.Identifier.InnerText + 'Enabled' = $Enabled 'Name' = $_.trustee.name.'#Text' 'Sid' = $_.trustee.SID.'#Text' + #'SidType' = if (($XMLContent.GPO.SecurityDescriptor.Owner.SID.'#text').Length -le 10) { 'WellKnown' } else { 'Other' } 'PermissionType' = $_.type.PermissionType - 'Inherited' = $_.Inherited + 'Inherited' = if ($_.Inherited -eq 'false') { $false } else { $true } 'Permissions' = $_.Standard.GPOGroupedAccessEnum } } } - 'Auditing' = if ($XMLContent.GPO.SecurityDescriptor.AuditingPresent.'#text' -eq 'true') { $true } else { $false } - 'Links' = $XMLContent.GPO.LinksTo | ForEach-Object -Process { - if ($_) { - [PSCustomObject] @{ - CanonicalName = $_.SOMPath - Enabled = $_.Enabled - NoOverride = $_.NoOverride + } else { + [PsCustomObject] @{ + 'DisplayName' = $XMLContent.GPO.Name + 'DomainName' = $XMLContent.GPO.Identifier.Domain.'#text' + 'GUID' = $XMLContent.GPO.Identifier.Identifier.InnerText + 'Linked' = $Linked + 'LinksCount' = $LinksCount + 'Enabled' = $Enabled + 'ComputerEnabled' = $ComputerEnabled + 'UserEnabled' = $UserEnabled + 'ComputerSettingsAvailable' = if ($null -eq $XMLContent.GPO.Computer.ExtensionData) { $false } else { $true } + 'UserSettingsAvailable' = if ($null -eq $XMLContent.GPO.User.ExtensionData) { $false } else { $true } + 'ComputerSettingsStatus' = if ($XMLContent.GPO.Computer.VersionDirectory -eq 0 -and $XMLContent.GPO.Computer.VersionSysvol -eq 0) { "NeverModified" } else { "Modified" } + 'ComputerSetttingsVersionIdentical' = if ($XMLContent.GPO.Computer.VersionDirectory -eq $XMLContent.GPO.Computer.VersionSysvol) { $true } else { $false } + 'ComputerSettings' = $XMLContent.GPO.Computer.ExtensionData.Extension + 'UserSettingsStatus' = if ($XMLContent.GPO.User.VersionDirectory -eq 0 -and $XMLContent.GPO.User.VersionSysvol -eq 0) { "NeverModified" } else { "Modified" } + 'UserSettingsVersionIdentical' = if ($XMLContent.GPO.User.VersionDirectory -eq $XMLContent.GPO.User.VersionSysvol) { $true } else { $false } + 'UserSettings' = $XMLContent.GPO.User.ExtensionData.Extension + + 'CreationTime' = [DateTime] $XMLContent.GPO.CreatedTime + 'ModificationTime' = [DateTime] $XMLContent.GPO.ModifiedTime + 'ReadTime' = [DateTime] $XMLContent.GPO.ReadTime + + 'WMIFilter' = $GPO.WmiFilter.name + 'WMIFilterDescription' = $GPO.WmiFilter.Description + 'DistinguishedName' = $GPO.Path + 'SDDL' = if ($Splitter -ne '') { $XMLContent.GPO.SecurityDescriptor.SDDL.'#text' -join $Splitter } else { $XMLContent.GPO.SecurityDescriptor.SDDL.'#text' } + 'Owner' = $XMLContent.GPO.SecurityDescriptor.Owner.Name.'#text' + 'OwnerSID' = $XMLContent.GPO.SecurityDescriptor.Owner.SID.'#text' + 'ACL' = @( + [PsCustomObject] @{ + 'Name' = $XMLContent.GPO.SecurityDescriptor.Owner.Name.'#text' + 'Sid' = $XMLContent.GPO.SecurityDescriptor.Owner.SID.'#text' + 'PermissionType' = 'Allow' + 'Inherited' = $false + 'Permissions' = 'Owner' + } + $XMLContent.GPO.SecurityDescriptor.Permissions.TrusteePermissions | ForEach-Object -Process { + if ($_) { + [PsCustomObject] @{ + 'Name' = $_.trustee.name.'#Text' + 'Sid' = $_.trustee.SID.'#Text' + 'PermissionType' = $_.type.PermissionType + 'Inherited' = if ($_.Inherited -eq 'false') { $false } else { $true } + 'Permissions' = $_.Standard.GPOGroupedAccessEnum + } + } + } + ) + 'Auditing' = if ($XMLContent.GPO.SecurityDescriptor.AuditingPresent.'#text' -eq 'true') { $true } else { $false } + 'Links' = $XMLContent.GPO.LinksTo | ForEach-Object -Process { + if ($_) { + [PSCustomObject] @{ + CanonicalName = $_.SOMPath + Enabled = $_.Enabled + NoOverride = $_.NoOverride + } } } - } - <# + <# SOMName SOMPath Enabled NoOverride ------- ------- ------- ---------- ad ad.evotec.xyz true false #> - #| Select-Object -ExpandProperty SOMPath + #| Select-Object -ExpandProperty SOMPath + } } #break } \ No newline at end of file diff --git a/Private/New-ADForestDrives.ps1 b/Private/New-ADForestDrives.ps1 new file mode 100644 index 0000000..1603663 --- /dev/null +++ b/Private/New-ADForestDrives.ps1 @@ -0,0 +1,56 @@ +function New-ADForestDrives { + [cmdletbinding()] + param( + [string] $ForestName, + [string] $ObjectDN + ) + if (-not $Global:ADDrivesMapped) { + if ($ForestName) { + $Forest = Get-ADForest -Identity $ForestName + } else { + $Forest = Get-ADForest + } + if ($ObjectDN) { + # This doesn't work because no Domain and no $Server + $DNConverted = (ConvertFrom-Distinguishedname -DistinguishedName $ObjectDN -ToDC) -replace '=' -replace ',' + if (-not(Get-PSDrive -Name $DNConverted -ErrorAction SilentlyContinue)) { + try { + + if ($Server) { + $null = New-PSDrive -Name $DNConverted -Root '' -PsProvider ActiveDirectory -Server $Server.Hostname[0] -Scope Global -WhatIf:$false + Write-Verbose "New-ADForestDrives - Mapped drive $Domain / $($Server.Hostname[0])" + } else { + $null = New-PSDrive -Name $DNConverted -Root '' -PsProvider ActiveDirectory -Server $Domain -Scope Global -WhatIf:$false + } + } catch { + Write-Warning "New-ADForestDrives - Couldn't map new AD psdrive for $Domain / $($Server.Hostname[0])" + } + } + } else { + foreach ($Domain in $Forest.Domains) { + try { + $Server = Get-ADDomainController -Discover -DomainName $Domain + $DomainInformation = Get-ADDomain -Server $Server.Hostname[0] + } catch { + Write-Warning "New-ADForestDrives - Can't process domain $Domain - $($_.Exception.Message)" + continue + } + $ObjectDN = $DomainInformation.DistinguishedName + $DNConverted = (ConvertFrom-Distinguishedname -DistinguishedName $ObjectDN -ToDC) -replace '=' -replace ',' + if (-not(Get-PSDrive -Name $DNConverted -ErrorAction SilentlyContinue)) { + try { + if ($Server) { + $null = New-PSDrive -Name $DNConverted -Root '' -PsProvider ActiveDirectory -Server $Server.Hostname[0] -Scope Global -WhatIf:$false + Write-Verbose "New-ADForestDrives - Mapped drive $Domain / $Server" + } else { + $null = New-PSDrive -Name $DNConverted -Root '' -PsProvider ActiveDirectory -Server $Domain -Scope Global -WhatIf:$false + } + } catch { + Write-Warning "New-ADForestDrives - Couldn't map new AD psdrive for $Domain / $Server $($_.Exception.Message)" + } + } + } + } + $Global:ADDrivesMapped = $true + } +} \ No newline at end of file diff --git a/Public/Backup-GPOZaurr.ps1 b/Public/Backup-GPOZaurr.ps1 index 50b726f..205c2f4 100644 --- a/Public/Backup-GPOZaurr.ps1 +++ b/Public/Backup-GPOZaurr.ps1 @@ -2,7 +2,7 @@ [cmdletBinding(SupportsShouldProcess)] param( [int] $LimitProcessing, - [validateset('All', 'Empty', 'Unlinked', 'EmptyAndUnlinked')][string] $Type = 'All', + [validateset('All', 'Empty', 'Unlinked')][string[]] $Type = 'All', [alias('ForestName')][string] $Forest, [string[]] $ExcludeDomains, [alias('Domain', 'Domains')][string[]] $IncludeDomains, @@ -23,67 +23,49 @@ } Process { Get-GPOZaurr -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation -GPOPath $GPOPath | ForEach-Object { - #$ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation - #$GPOSummary = foreach ($GPO in $GPOs) { - #$QueryServer = $ForestInformation['QueryServers'][$_.Domain]['HostName'][0] - if ($Type -eq 'All') { - Write-Verbose "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain)" + if ($Type -contains 'All') { + Write-Verbose "Backup-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName)" $Count++ try { - $BackupInfo = Backup-GPO -Guid $_.GUID -Domain $_.Domain -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer + $BackupInfo = Backup-GPO -Guid $_.GUID -Domain $_.DomainName -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer $BackupInfo } catch { - Write-Warning "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" + Write-Warning "Backup-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName) failed: $($_.Exception.Message)" } if ($LimitProcessing -eq $Count) { break } - } elseif ($Type -eq 'Empty') { + } + if ($Type -notcontains 'All' -and $Type -contains 'Empty') { if ($_.ComputerSettingsAvailable -eq $false -and $_.UserSettingsAvailable -eq $false) { - Write-Verbose "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain)" + Write-Verbose "Backup-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName)" $Count++ try { - $BackupInfo = Backup-GPO -Guid $_.GUID -Domain $_.Domain -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer + $BackupInfo = Backup-GPO -Guid $_.GUID -Domain $_.DomainName -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer $BackupInfo } catch { - Write-Warning "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" - } - if ($LimitProcessing -eq $Count) { - break - } - } - } elseif ($Type -eq 'EmptyAndUnlinked') { - if ($_.ComputerSettingsAvailable -eq $false -and $_.UserSettingsAvailable -eq $false -or $_.Linked -eq $false) { - Write-Verbose "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain)" - $Count++ - try { - $BackupInfo = Backup-GPO -Guid $_.GUID -Domain $_.Domain -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer - $BackupInfo - } catch { - Write-Warning "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" - } - if ($LimitProcessing -eq $Count) { - break - } - } - } elseif ($Type -eq 'Unlinked') { - if ($_.Linked -eq $false) { - Write-Verbose "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain)" - $Count++ - try { - $BackupInfo = Backup-GPO -Guid $_.GUID -Domain $_.Domain -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer - $BackupInfo - } catch { - Write-Warning "Backup-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" + Write-Warning "Backup-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName) failed: $($_.Exception.Message)" + } + if ($LimitProcessing -eq $Count) { + break + } + } + } + if ($Type -notcontains 'All' -and $Type -contains 'Unlinked') { + if ($_.Linked -eq $false) { + Write-Verbose "Backup-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName)" + $Count++ + try { + $BackupInfo = Backup-GPO -Guid $_.GUID -Domain $_.DomainName -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer + $BackupInfo + } catch { + Write-Warning "Backup-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName) failed: $($_.Exception.Message)" } if ($LimitProcessing -eq $Count) { break } } } - - #} - #$GPOSummary } } End { diff --git a/Public/Get-GPOZaurr.ps1 b/Public/Get-GPOZaurr.ps1 index 16e3f3b..ab277ad 100644 --- a/Public/Get-GPOZaurr.ps1 +++ b/Public/Get-GPOZaurr.ps1 @@ -1,11 +1,17 @@ function Get-GPOZaurr { [cmdletBinding()] param( + [string] $GPOName, + [alias('GUID', 'GPOID')][string] $GPOGuid, + [alias('ForestName')][string] $Forest, [string[]] $ExcludeDomains, [alias('Domain', 'Domains')][string[]] $IncludeDomains, [System.Collections.IDictionary] $ExtendedForestInformation, - [string[]] $GPOPath + [string[]] $GPOPath, + + [switch] $PermissionsOnly, + [switch] $Limited ) Begin { if (-not $GPOPath) { @@ -15,10 +21,37 @@ Process { if (-not $GPOPath) { foreach ($Domain in $ForestInformation.Domains) { - Get-GPO -All -Server $ForestInformation.QueryServers[$Domain].HostName[0] -Domain $Domain | ForEach-Object { - Write-Verbose "Get-GPOZaurr - Getting GPO $($_.DisplayName) / ID: $($_.ID) from $Domain" - $XMLContent = Get-GPOReport -ID $_.ID -ReportType XML -Server $ForestInformation.QueryServers[$Domain].HostName[0] -Domain $Domain - Get-XMLGPO -XMLContent $XMLContent -GPO $_ + $QueryServer = $ForestInformation.QueryServers[$Domain]['HostName'][0] + if ($GPOName) { + Get-GPO -Name $GPOName -Domain $Domain -Server $QueryServer -ErrorAction SilentlyContinue | ForEach-Object { + Write-Verbose "Get-GPOZaurr - Getting GPO $($_.DisplayName) / ID: $($_.ID) from $Domain" + if (-not $Limited) { + $XMLContent = Get-GPOReport -ID $_.ID -ReportType XML -Server $ForestInformation.QueryServers[$Domain].HostName[0] -Domain $Domain + Get-XMLGPO -XMLContent $XMLContent -GPO $_ -PermissionsOnly:$PermissionsOnly.IsPresent + } else { + $_ + } + } + } elseif ($GPOGuid) { + Get-GPO -Guid $GPOGuid -Domain $Domain -Server $QueryServer -ErrorAction SilentlyContinue | ForEach-Object { + Write-Verbose "Get-GPOZaurr - Getting GPO $($_.DisplayName) / ID: $($_.ID) from $Domain" + if (-not $Limited) { + $XMLContent = Get-GPOReport -ID $_.ID -ReportType XML -Server $ForestInformation.QueryServers[$Domain].HostName[0] -Domain $Domain + Get-XMLGPO -XMLContent $XMLContent -GPO $_ -PermissionsOnly:$PermissionsOnly.IsPresent + } else { + $_ + } + } + } else { + Get-GPO -All -Server $QueryServer -Domain $Domain -ErrorAction SilentlyContinue | ForEach-Object { + Write-Verbose "Get-GPOZaurr - Getting GPO $($_.DisplayName) / ID: $($_.ID) from $Domain" + if (-not $Limited) { + $XMLContent = Get-GPOReport -ID $_.ID -ReportType XML -Server $ForestInformation.QueryServers[$Domain].HostName[0] -Domain $Domain + Get-XMLGPO -XMLContent $XMLContent -GPO $_ -PermissionsOnly:$PermissionsOnly.IsPresent + } else { + $_ + } + } } } } else { @@ -26,7 +59,7 @@ Get-ChildItem -LiteralPath $Path -Recurse -Filter *.xml | ForEach-Object { $XMLContent = [XML]::new() $XMLContent.Load($_.FullName) - Get-XMLGPO -XMLContent $XMLContent + Get-XMLGPO -XMLContent $XMLContent -PermissionsOnly:$PermissionsOnly.IsPresent } } } diff --git a/Public/Get-GPOZaurrBackupInformation.ps1 b/Public/Get-GPOZaurrBackupInformation.ps1 index 50d3dee..b6bcca1 100644 --- a/Public/Get-GPOZaurrBackupInformation.ps1 +++ b/Public/Get-GPOZaurrBackupInformation.ps1 @@ -14,7 +14,7 @@ $Xml.Backups.BackupInst | ForEach-Object { [PSCustomObject] @{ DisplayName = $_.GPODisplayName.'#cdata-section' - Domain = $_.GPODomain.'#cdata-section' + DomainName = $_.GPODomain.'#cdata-section' Guid = $_.GPOGUid.'#cdata-section' DomainGuid = $_.GPODomainGuid.'#cdata-section' DomainController = $_.GPODomainController.'#cdata-section' diff --git a/Public/Get-GPOZaurrPermission.ps1 b/Public/Get-GPOZaurrPermission.ps1 new file mode 100644 index 0000000..84bdafd --- /dev/null +++ b/Public/Get-GPOZaurrPermission.ps1 @@ -0,0 +1,80 @@ +function Get-GPOZaurrPermission { + [cmdletBinding()] + param( + [switch] $SkipWellKnownGroup, + [alias('ForestName')][string] $Forest, + [string[]] $ExcludeDomains, + [alias('Domain', 'Domains')][string[]] $IncludeDomains, + [System.Collections.IDictionary] $ExtendedForestInformation + ) + Begin { + if ($Type -contains 'NonAdministrative') { + $ADAdministrativeGroups = Get-ADADministrativeGroups -Type DomainAdmins, EnterpriseAdmins -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation + } + #$Count = 0 + } + Process { + $ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation + foreach ($Domain in $ForestInformation.Domains) { + $QueryServer = $ForestInformation['QueryServers'][$Domain]['HostName'][0] + Get-GPO -All -Domain $Domain -Server $QueryServer | ForEach-Object -Process { + $GPO = $_ + Write-Verbose "Get-GPOZaurrPermission - Processing $($GPO.DisplayName) from $($GPO.DomainName)" + Get-GPPermissions -Guid $GPO.ID -DomainName $GPO.DomainName -All -Server $QueryServer | ForEach-Object -Process { + $GPOPermission = $_ + [PSCustomObject] @{ + DisplayName = $GPO.DisplayName # : ALL | Enable RDP + GUID = $GPO.ID + DomainName = $GPO.DomainName # : ad.evotec.xyz + Enabled = $GPO.GpoStatus + Description = $GPO.Description + CreationDate = $GPO.CreationTime + ModificationTime = $GPO.ModificationTime + Permission = $GPOPermission.Permission # : GpoEditDeleteModifySecurity + Inherited = $GPOPermission.Inherited # : False + Domain = $GPOPermission.Trustee.Domain #: EVOTEC + DistinguishedName = $GPOPermission.Trustee.DSPath #: CN = Domain Admins, CN = Users, DC = ad, DC = evotec, DC = xyz + Name = $GPOPermission.Trustee.Name #: Domain Admins + Sid = $GPOPermission.Trustee.Sid #: S - 1 - 5 - 21 - 853615985 - 2870445339 - 3163598659 - 512 + SidType = $GPOPermission.Trustee.SidType #: Group + } + } + if ($GPO.Owner) { + $SplittedOwner = $GPO.Owner.Split('\') + $DomainOwner = $SplittedOwner[0] #: EVOTEC + $DomainUserName = $SplittedOwner[1] #: Domain Admins + $SID = $ADAdministrativeGroups['ByNetBIOS']["$($GPO.Owner)"].Sid + if ($SID) { + $SIDType = 'Group' + } else { + $SIDType = '' + } + } else { + $DomainOwner = $GPO.Owner + $DomainUserName = '' + $SID = '' + $SIDType = '' + } + [PSCustomObject] @{ + DisplayName = $GPO.DisplayName # : ALL | Enable RDP + GUID = $GPO.GUID + DomainName = $GPO.DomainName # : ad.evotec.xyz + Enabled = $GPO.GpoStatus + Description = $GPO.Description + CreationDate = $GPO.CreationTime + ModificationTime = $GPO.ModificationTime + Permission = 'GpoOwner' # : GpoEditDeleteModifySecurity + Inherited = $false # : False + Domain = $DomainOwner + DistinguishedName = '' #: CN = Domain Admins, CN = Users, DC = ad, DC = evotec, DC = xyz + Name = $DomainUserName + Sid = $SID #: S - 1 - 5 - 21 - 853615985 - 2870445339 - 3163598659 - 512 + SidType = $SIDType # #: Group + } + } + } + } + End { + + } +} \ No newline at end of file diff --git a/Public/Get-GPOZaurrPermissions.ps1 b/Public/Get-GPOZaurrPermissions.ps1 deleted file mode 100644 index edb31cd..0000000 --- a/Public/Get-GPOZaurrPermissions.ps1 +++ /dev/null @@ -1,83 +0,0 @@ -function Get-GPOZaurrPermissions { - [cmdletBinding()] - param( - [switch] $SkipWellKnownGroup, - [alias('ForestName')][string] $Forest, - [string[]] $ExcludeDomains, - [alias('Domain', 'Domains')][string[]] $IncludeDomains, - [System.Collections.IDictionary] $ExtendedForestInformation - ) - $ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation - foreach ($Domain in $ForestInformation.Domains) { - $QueryServer = $ForestInformation['QueryServers'][$Domain]['HostName'][0] - Get-GPO -All -Domain $Domain -Server $QueryServer | ForEach-Object -Process { - $GPO = $_ - - <# - DisplayName : ALL | Enable RDP - DomainName : ad.evotec.xyz - Owner : EVOTEC\Domain Admins - Id : 051bcddf-cc11-427b-bdf0-684c0a6e3ddb - GpoStatus : AllSettingsEnabled - Description : - CreationTime : 07.08.2018 12:47:44 - ModificationTime : 07.04.2020 22:09:24 - UserVersion : AD Version: 1, SysVol Version: 1 - ComputerVersion : AD Version: 1, SysVol Version: 1 - WmiFilter : - #> - Get-GPPermissions -Guid $GPO.ID -DomainName $GPO.DomainName -All -Server $QueryServer | ForEach-Object -Process { - $GPOPermission = $_ - #$GPOPermissionFormatted = ConvertTo-TableFormat -InputObject $_ - [PSCustomObject] @{ - DisplayName = $GPO.DisplayName # : ALL | Enable RDP - GUID = $GPO.ID - DomainName = $GPO.DomainName # : ad.evotec.xyz - Enabled = $GPO.GpoStatus - Description = $GPO.Description - CreationDate = $GPO.CreationTime - ModificationTime = $GPO.ModificationTime - #Owner = $GPO.Owner # : EVOTEC\Domain Admins - #Trustee = $GPOPermission.Trustee # : Domain Admins - #TrusteeType = $GPOPermissionFormatted.TrusteeType # # : Group - Permission = $GPOPermission.Permission # : GpoEditDeleteModifySecurity - Inherited = $GPOPermission.Inherited # : False - Domain = $GPOPermission.Trustee.Domain #: EVOTEC - DistinguishedName = $GPOPermission.Trustee.DSPath #: CN = Domain Admins, CN = Users, DC = ad, DC = evotec, DC = xyz - Name = $GPOPermission.Trustee.Name #: Domain Admins - Sid = $GPOPermission.Trustee.Sid #: S - 1 - 5 - 21 - 853615985 - 2870445339 - 3163598659 - 512 - SidType = $GPOPermission.Trustee.SidType #: Group - } - } - - if ($GPO.Owner) { - $SplittedOwner = $GPO.Owner.Split('\') - $DomainOwner = $SplittedOwner[0] #: EVOTEC - $DomainUserName = $SplittedOwner[1] #: Domain Admins - } else { - $DomainOwner = $GPO.Owner - $DomainUserName = '' - } - [PSCustomObject] @{ - DisplayName = $GPO.DisplayName # : ALL | Enable RDP - GUID = $GPO.GUID - DomainName = $GPO.DomainName # : ad.evotec.xyz - #Owner = $GPO.Owner # : EVOTEC\Domain Admins - #Trustee = $GPOPermission.Trustee # : Domain Admins - #TrusteeType = $GPOPermissionFormatted.TrusteeType # # : Group - Enabled = $GPO.GpoStatus - Description = $GPO.Description - CreationDate = $GPO.CreationTime - ModificationTime = $GPO.ModificationTime - - Permission = 'Owner' # : GpoEditDeleteModifySecurity - Inherited = $false # : False - Domain = $DomainOwner - DistinguishedName = '' #: CN = Domain Admins, CN = Users, DC = ad, DC = evotec, DC = xyz - Name = $DomainUserName - Sid = '' #: S - 1 - 5 - 21 - 853615985 - 2870445339 - 3163598659 - 512 - SidType = '' #: Group - } - } - } -} \ No newline at end of file diff --git a/Public/Get-GPOZaurrWmi.ps1 b/Public/Get-GPOZaurrWmi.ps1 index fb9d8f8..92a4e7c 100644 --- a/Public/Get-GPOZaurrWmi.ps1 +++ b/Public/Get-GPOZaurrWmi.ps1 @@ -20,9 +20,9 @@ Get-ADObject -LDAPFilter $ldapFilter -Properties $wmiFilterAttr -Server $QueryServer | ForEach-Object -Process { $WMI = $_.'msWMI-Parm2' -split ';' [PSCustomObject] @{ - Name = $_.'msWMI-Name' + DisplayName = $_.'msWMI-Name' Description = $_.'msWMI-Parm1' - Domain = $Domain + DomainName = $Domain NameSpace = $WMI[5] Query = $WMI[6] Author = $_.'msWMI-Author' @@ -44,9 +44,9 @@ Get-ADObject -LDAPFilter $ldapFilter -Properties $wmiFilterAttr -Server $QueryServer | ForEach-Object -Process { $WMI = $_.'msWMI-Parm2' -split ';' [PSCustomObject] @{ - Name = $_.'msWMI-Name' + DisplayName = $_.'msWMI-Name' Description = $_.'msWMI-Parm1' - Domain = $Domain + DomainName = $Domain NameSpace = $WMI[5] Query = $WMI[6] Author = $_.'msWMI-Author' @@ -68,9 +68,9 @@ Get-ADObject -LDAPFilter $ldapFilter -Properties $wmiFilterAttr -Server $QueryServer | ForEach-Object -Process { $WMI = $_.'msWMI-Parm2' -split ';' [PSCustomObject] @{ - Name = $_.'msWMI-Name' + DisplayName = $_.'msWMI-Name' Description = $_.'msWMI-Parm1' - Domain = $Domain + DomainName = $Domain NameSpace = $WMI[5] Query = $WMI[6] Author = $_.'msWMI-Author' diff --git a/Public/New-GPOZaurrWMi.ps1 b/Public/New-GPOZaurrWMi.ps1 index fd0b97b..efedfdc 100644 --- a/Public/New-GPOZaurrWMi.ps1 +++ b/Public/New-GPOZaurrWMi.ps1 @@ -74,7 +74,7 @@ } } else { foreach ($_ in $ExistingWmiFilter) { - Write-Warning "New-GPOZaurrWMI - Skipping creation of GPO because name: $($_.Name) guid: $($_.ID) for $($_.Domain) already exists." + Write-Warning "New-GPOZaurrWMI - Skipping creation of GPO because name: $($_.DisplayName) guid: $($_.ID) for $($_.DomainName) already exists." } } } diff --git a/Public/Remove-GPOZaurr.ps1 b/Public/Remove-GPOZaurr.ps1 index 613df50..dfde4e2 100644 --- a/Public/Remove-GPOZaurr.ps1 +++ b/Public/Remove-GPOZaurr.ps1 @@ -1,7 +1,7 @@ function Remove-GPOZaurr { [cmdletBinding(SupportsShouldProcess)] param( - [parameter(Mandatory)][validateset('Empty', 'Unlinked', 'EmptyAndUnlinked')][string] $Type, + [parameter(Mandatory)][validateset('Empty', 'Unlinked')][string[]] $Type, [int] $LimitProcessing, [alias('ForestName')][string] $Forest, [string[]] $ExcludeDomains, @@ -28,77 +28,49 @@ } Process { Get-GPOZaurr -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation -GPOPath $GPOPath | ForEach-Object { - #$ForestInformation = Get-WinADForestDetails -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation - - #$GPOSummary = foreach ($GPO in $GPOs) { - #$QueryServer = $ForestInformation['QueryServers'][$_.Domain]['HostName'][0] - if ($Type -eq 'Empty') { + if ($Type -contains 'Empty') { if ($_.ComputerSettingsAvailable -eq $false -and $_.UserSettingsAvailable -eq $false) { if ($BackupRequired) { try { - Write-Verbose "Remove-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain)" - $BackupInfo = Backup-GPO -Guid $_.Guid -Domain $_.Domain -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer + Write-Verbose "Remove-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName)" + $BackupInfo = Backup-GPO -Guid $_.Guid -Domain $_.DomainName -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer $BackupInfo } catch { - Write-Warning "Remove-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" + Write-Warning "Remove-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName) failed: $($_.Exception.Message)" } } if (($BackupRequired -and $BackupInfo) -or (-not $BackupRequired)) { try { - Write-Verbose "Remove-GPOZaurr - Removing GPO $($_.Name) from $($_.Domain)" - Remove-GPO -Domain $_.Domain -Guid $_.Guid -ErrorAction Stop #-Server $QueryServer + Write-Verbose "Remove-GPOZaurr - Removing GPO $($_.DisplayName) from $($_.DomainName)" + Remove-GPO -Domain $_.DomainName -Guid $_.Guid -ErrorAction Stop #-Server $QueryServer } catch { - Write-Warning "Remove-GPOZaurr - Removing GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" - } - } - $Count++ - if ($LimitProcessing -eq $Count) { - break - } - } - } elseif ($Type -eq 'EmptyAndUnlinked') { - if ($_.ComputerSettingsAvailable -eq $false -and $_.UserSettingsAvailable -eq $false -or $_.Linked -eq $false) { - - if ($BackupRequired) { - try { - Write-Verbose "Remove-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain)" - $BackupInfo = Backup-GPO -Guid $_.Guid -Domain $_.Domain -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer - $BackupInfo - } catch { - Write-Warning "Remove-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" - } - } - if (($BackupRequired -and $BackupInfo) -or (-not $BackupRequired)) { - try { - Write-Verbose "Remove-GPOZaurr - Removing GPO $($_.Name) from $($_.Domain)" - Remove-GPO -Domain $_.Domain -Guid $_.Guid -ErrorAction Stop #-Server $QueryServer - } catch { - Write-Warning "Remove-GPOZaurr - Removing GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" - } - } - $Count++ - if ($LimitProcessing -eq $Count) { - break - } - } - } elseif ($Type -eq 'Unlinked') { - if ($_.Linked -eq $false) { - if ($BackupRequired) { - try { - Write-Verbose "Remove-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain)" - $BackupInfo = Backup-GPO -Guid $_.Guid -Domain $_.Domain -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer - $BackupInfo - } catch { - Write-Warning "Remove-GPOZaurr - Backing up GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" - } - } - if (($BackupRequired -and $BackupInfo) -or (-not $BackupRequired)) { - try { - Write-Verbose "Remove-GPOZaurr - Removing GPO $($_.Name) from $($_.Domain)" - Remove-GPO -Domain $_.Domain -Guid $_.Guid -ErrorAction Stop #-Server $QueryServer - } catch { - Write-Warning "Remove-GPOZaurr - Removing GPO $($_.Name) from $($_.Domain) failed: $($_.Exception.Message)" + Write-Warning "Remove-GPOZaurr - Removing GPO $($_.DisplayName) from $($_.DomainName) failed: $($_.Exception.Message)" + } + } + $Count++ + if ($LimitProcessing -eq $Count) { + break + } + } + } + if ($Type -contains 'Unlinked') { + if ($_.Linked -eq $false) { + if ($BackupRequired) { + try { + Write-Verbose "Remove-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName)" + $BackupInfo = Backup-GPO -Guid $_.Guid -Domain $_.DomainName -Path $BackupFinalPath -ErrorAction Stop #-Server $QueryServer + $BackupInfo + } catch { + Write-Warning "Remove-GPOZaurr - Backing up GPO $($_.DisplayName) from $($_.DomainName) failed: $($_.Exception.Message)" + } + } + if (($BackupRequired -and $BackupInfo) -or (-not $BackupRequired)) { + try { + Write-Verbose "Remove-GPOZaurr - Removing GPO $($_.DisplayName) from $($_.DomainName)" + Remove-GPO -Domain $_.DomainName -Guid $_.Guid -ErrorAction Stop #-Server $QueryServer + } catch { + Write-Warning "Remove-GPOZaurr - Removing GPO $($_.DisplayName) from $($_.DomainName) failed: $($_.Exception.Message)" } } $Count++ @@ -107,8 +79,6 @@ } } } - #} - #$GPOSummary } } End { diff --git a/Public/Remove-GPOZaurrPermission.ps1 b/Public/Remove-GPOZaurrPermission.ps1 new file mode 100644 index 0000000..b3e6d46 --- /dev/null +++ b/Public/Remove-GPOZaurrPermission.ps1 @@ -0,0 +1,13 @@ +function Remove-GPOZaurrPermission { + [cmdletBinding()] + param( + [string] $Type, + [alias('ForestName')][string] $Forest, + [string[]] $ExcludeDomains, + [alias('Domain', 'Domains')][string[]] $IncludeDomains, + [System.Collections.IDictionary] $ExtendedForestInformation + ) + Get-GPOZaurrPermission -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation | ForEach-Object -Process { + Write-Verbose "Remove-GPOZaurrPermission - Test" + } +} \ No newline at end of file diff --git a/Public/Restore-GPOZaurr.ps1 b/Public/Restore-GPOZaurr.ps1 index c34e939..569418b 100644 --- a/Public/Restore-GPOZaurr.ps1 +++ b/Public/Restore-GPOZaurr.ps1 @@ -13,7 +13,7 @@ if (-not $SkipBackupSummary) { $BackupSummary = Get-GPOZaurrBackupInformation -BackupFolder $BackupFolder if ($Domain) { - [Array] $FoundGPO = $BackupSummary | Where-Object { $_.DisplayName -eq $DisplayName -and $_.Domain -eq $Domain } + [Array] $FoundGPO = $BackupSummary | Where-Object { $_.DisplayName -eq $DisplayName -and $_.DomainName -eq $Domain } } else { [Array] $FoundGPO = $BackupSummary | Where-Object { $_.DisplayName -eq $DisplayName } } @@ -21,11 +21,11 @@ if ($NewDisplayName) { Import-GPO -Path $BackupFolder -BackupID $GPO.ID -Domain $GPO.Domain -TargetName $NewDisplayName -CreateIfNeeded } else { - Write-Verbose "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.Domain) / BackupId: $($GPO.ID)" + Write-Verbose "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.DomainName) / BackupId: $($GPO.ID)" try { - Restore-GPO -Path $BackupFolder -BackupID $GPO.ID -Domain $GPO.Domain + Restore-GPO -Path $BackupFolder -BackupID $GPO.ID -Domain $GPO.DomainName } catch { - Write-Warning "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.Domain) failed: $($_.Exception.Message)" + Write-Warning "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.DomainName) failed: $($_.Exception.Message)" } } } @@ -49,11 +49,11 @@ } else { $BackupSummary = Get-GPOZaurrBackupInformation -BackupFolder $BackupFolder foreach ($GPO in $BackupSummary) { - Write-Verbose "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.Domain) / BackupId: $($GPO.ID)" + Write-Verbose "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.DomainName) / BackupId: $($GPO.ID)" try { - Restore-GPO -Path $BackupFolder -Domain $GPO.Domain -BackupId $GPO.ID + Restore-GPO -Path $BackupFolder -Domain $GPO.DomainName -BackupId $GPO.ID } catch { - Write-Warning "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.Domain) failed: $($_.Exception.Message)" + Write-Warning "Restore-GPOZaurr - Restoring GPO $($GPO.DisplayName) from $($GPO.DomainName) failed: $($_.Exception.Message)" } } } diff --git a/Public/Set-GPOZaurrOwner.ps1 b/Public/Set-GPOZaurrOwner.ps1 new file mode 100644 index 0000000..be00cc0 --- /dev/null +++ b/Public/Set-GPOZaurrOwner.ps1 @@ -0,0 +1,86 @@ +function Set-GPOZaurrOwner { + [cmdletBinding(SupportsShouldProcess, DefaultParameterSetName = 'Type')] + param( + [Parameter(ParameterSetName = 'Type', Mandatory)] + [validateset('EmptyOrUnknown', 'NonAdministrative')][string[]] $Type, + + [Parameter(ParameterSetName = 'Named')][string] $GPOName, + [Parameter(ParameterSetName = 'Named')][alias('GUID', 'GPOID')][string] $GPOGuid, + + [Parameter(ParameterSetName = 'Type')] + [Parameter(ParameterSetName = 'Named')] + [alias('ForestName')][string] $Forest, + + [Parameter(ParameterSetName = 'Type')] + [Parameter(ParameterSetName = 'Named')] + [string[]] $ExcludeDomains, + + [Parameter(ParameterSetName = 'Type')] + [Parameter(ParameterSetName = 'Named')] + [alias('Domain', 'Domains')][string[]] $IncludeDomains, + + [Parameter(ParameterSetName = 'Type')] + [Parameter(ParameterSetName = 'Named')] + [System.Collections.IDictionary] $ExtendedForestInformation, + + [Parameter(Mandatory, ParameterSetName = 'Named')] + [string] $Principal, + + [Parameter(ParameterSetName = 'Type')] + [Parameter(ParameterSetName = 'Named')] + [int] $LimitProcessing + ) + Begin { + if ($Type -contains 'NonAdministrative') { + $ADAdministrativeGroups = Get-ADADministrativeGroups -Type DomainAdmins, EnterpriseAdmins -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation + } + $Count = 0 + } + Process { + if ($Type) { + Get-GPOZaurr -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation -Verbose:$false | ForEach-Object -Process { + $GPO = $_ + if ($Type -contains 'NonAdministrative') { + if ($GPO.Owner) { + $AdministrativeGroup = $ADAdministrativeGroups['ByNetBIOS']["$($GPO.Owner)"] + $DefaultPrincipal = $ADAdministrativeGroups["$($GPO.DomainName)"]['DomainAdmins'] + if ($AdministrativeGroup) { + #Write-Verbose "Set-GPOZaurrOwner - Skipping GPO: $($GPO.DisplayName) from domain: $($GPO.DomainName). Already owner $($GPO.Owner)." + } else { + Write-Verbose "Set-GPOZaurrOwner - Changing GPO: $($GPO.DisplayName) from domain: $($GPO.DomainName) from owner $($GPO.Owner) to $DefaultPrincipal" + Set-ADACLOwner -ADObject $GPO.DistinguishedName -Principal $DefaultPrincipal -Verbose:$false + $Count++ + if ($Count -eq $LimitProcessing) { + break + } + } + } + } + if ($Type -contains 'EmptyOrUnknown') { + if ($null -eq $GPO.Owner) { + $DefaultPrincipal = $ADAdministrativeGroups["$($GPO.DomainName)"]['DomainAdmins'] + Write-Verbose "Set-GPOZaurrOwner - Changing GPO: $($GPO.DisplayName) from domain: $($GPO.DomainName) from owner NULL/$($GPO.OwnerSID) to $DefaultPrincipal" + Set-ADACLOwner -ADObject $GPO.DistinguishedName -Principal $DefaultPrincipal -Verbose:$false + $Count++ + if ($Count -eq $LimitProcessing) { + break + } + } + } + } + } else { + Get-GPOZaurr -GPOName $GPOName -GPOGuid $GPOGUiD -Forest $Forest -IncludeDomains $IncludeDomains -ExcludeDomains $ExcludeDomains -ExtendedForestInformation $ExtendedForestInformation -Verbose:$false | ForEach-Object -Process { + $GPO = $_ + Write-Verbose "Set-GPOZaurrOwner - Changing GPO: $($GPO.DisplayName) from domain: $($GPO.DomainName) from owner $($GPO.Owner)/$($GPO.OwnerSID) to $Principal" + Set-ADACLOwner -ADObject $GPO.DistinguishedName -Principal $Principal -Verbose:$false + $Count++ + if ($Count -eq $LimitProcessing) { + break + } + } + } + } + End { + + } +} \ No newline at end of file diff --git a/Public/Set-GPOZaurrWMI.ps1 b/Public/Set-GPOZaurrWMI.ps1 new file mode 100644 index 0000000..740a6be --- /dev/null +++ b/Public/Set-GPOZaurrWMI.ps1 @@ -0,0 +1,6 @@ +function Set-GPOZaurrWMI { + [cmdletBinding()] + param( + + ) +} \ No newline at end of file