Site icon Franky's Web

Update Active Directory Shadow Groups

Some Active Directory features cannot be defined for organizational units but only for AD groups. One example of this is Fine Grained Password Policies. If you still want to apply such features to all users of an organizational unit, simply create a group with all users who are stored in the OU. This group is also called a shadow group. Here is an example:

However, it makes little sense to maintain these group memberships manually, as the members of the shadow groups quickly diverge and no longer reflect the actual users within the organizational unit.

Here, however, you can be helped by a small PowerShell script which, for example, is executed as a scheduled task every hour and updates the shadow groups.

The following script can help:

# Syntax:
# <distinguishedName of OU> = <AD Group Name>

$OUtoGroupList = @{
    "OU=OU1,OU=Benutzer,DC=frankysweblab,DC=de" = "ShadowGroup_OU1"
    "OU=OU2,OU=Benutzer,DC=frankysweblab,DC=de" = "ShadowGroup_OU2"
}

$OUtoGroupList.GetEnumerator() | ForEach-Object {
	$Group =  $_.value
	$OU = $_.key
	try {
		write-output "---> Processing OU $OU"
		$Users = Get-ADUser -Filter * -SearchBase $OU | select DistinguishedName
		$GroupMembers = Get-ADGroup $Group | Get-ADGroupMember | select DistinguishedName
		$CompareGroupMembership = Compare-Object -ReferenceObject $GroupMembers.DistinguishedName -DifferenceObject $users.DistinguishedName
	} catch {}

	
	if ($Users -and $CompareGroupMembership) {
		#Update group membership if OU contains users
		$UsersToAdd = $CompareGroupMembership | where {$_.SideIndicator -eq "=>"}
		foreach ($UsertoAdd in $UsersToAdd) {
			$UserDN = $UsertoAdd.InputObject
			write-output " Add user $user to group $group"
			Add-ADGroupMember -Identity $Group -Members $UserDN -confirm:$false
		}
	
		#Remove stalled users from group
		$UsersToRemove = $CompareGroupMembership | where {$_.SideIndicator -eq "<="}
		foreach ($UserToRemove in $UsersToRemove) {
			$UserDN = $UserToRemove.InputObject
			write-output " Remove user $UserDN from group $group"
			Remove-ADGroupMember -Identity $Group -Members $UserDN -confirm:$false
		}
	}
	elseif ($Users -and !$CompareGroupMembership) {
		#Add all users from OU to Group (if group was empty)
		write-output " Add all users to group $Group, group was empty"
		$Users | ForEach-Object { Add-ADGroupMember -Identity $Group -Members $_ }
	}
	elseif (!$Users) {
		#If no users in OU, delete all members from group
		write-output " No Users in OU $OU found, delete all members from group $Group"
		Get-ADGroup $Group | Set-ADGroup -clear member
	}
}

The first lines define which shadow group belongs to which OU. The shadow group does not have to be saved in the same OU, but can also be created in a separate OU. It is important that the groups are created beforehand, as the script does not create them.

When executed, the script updates the specified shadow groups and adds missing users to the group or removes them if the user accounts have been moved to another OU.

The script can also be downloaded from GitHub:

Exit mobile version