How to remove All Groups with Exceptions by using Powershell? - powershell

I've seen many examples of using PS to remove all memberships (including Primary). I have working code as follows:
get-aduser person -properties MemberOf | Select -Expand MemberOf | %{Remove-ADGroupMember $_ -member person -confirm:$false}
This is great for stripping everything out, excluding Domain Users. No problems so far.
The next challenge is leaving behind a specific group, such as licensing for O365.
I attempted to build an array with exclusions, and excluding those from the removal:
$user = person
$keep = #(
'CN=nametokeep,OU=group,DC=company,DC=com',
'CN=nametoalsokeep,OU=group,DC=company,DC=com')
$groups = get-aduser person -properties memberof | select -expand memberof
$groups | %{$keep -notcontains $_} | Remove-ADGroupMember -member $user
The idea here is to define the exceptions and remove everything else that doesn't match up.
When I do this, the code does execute but prompts for input:
Members[0]:
Doesn't matter what value I put in there, the code just prompts again with Members[1], Members[2] and so on.
What am I missing?

In order to remove "person" from all the groups not in the keep array, you will need to do a Foreach on each of the groups out of the $keep array so you iterate through them.
Also, Remove-ADGroupMember does not have a -Member parameter.
Parameter is -Members and that's what your powershell prompt is asking about when you run the cmdlet without it's mandatory parameter.
The following script should accomplish what you seek.
$user = 'Person'
$keep = #(
'CN=nametokeep,OU=group,DC=company,DC=com',
'CN=nametoalsokeep,OU=group,DC=company,DC=com'
)
$groups = get-aduser -Identity $user -properties memberof | select -expand memberof
$groups.Where({$_ -notin ($keep)}) |
% { Remove-ADGroupMember -Identity $_ -Members $user}
Reference
Remove-ADGroupMember

Related

Grabbing Specific AD Groups that a User is a Member Of

Just can't for the life of me figure this out. What I am trying to do is get a list of all the groups that a user is a member of. Then I would like to pass those along and grab the specific groups that I am looking for.
Below is what I have so far:
(Get-ADUser $user -Properties MemberOf ).MemberOf | Where-Object {$_.Name -contains 'Part of Group Name'}
This returns nothing. I have a feeling that I am not referencing the right property in my Where-Object but I am having a hard time finding what that is. I know the results of (Get-ADUser $user -Properties MemberOf ).MemberOf are:
CN=App - dyn_readuser_prod_WeblogicApps_NS,OU=Groups,OU=USCC,DC=int,DC=usc,DC=local
CN=App - dyn_readuser_prod_osb_NS,OU=Groups,OU=USCC,DC=int,DC=usc,DC=local
CN=App - dyn_readuser_prod_openshift_NS,OU=Groups,OU=USCC,DC=int,DC=usc,DC=local
CN=App - dyn_readuser_nonprod_WeblogicApps_NS,OU=Groups,OU=USCC,DC=int,DC=usc,DC=local
CN=App - dyn_readuser_nonprod_osb_NS,OU=Groups,OU=USCC,DC=int,DC=usc,DC=local
CN=App - dyn_readuser_nonprod_openshift_NS,OU=Groups,OU=USCC,DC=int,DC=usc,DC=local
I just can't figure out how to reference "CN".
Try it this way:
(Get-ADUser $user -Properties memberOf).memberOf |
Where-Object { $_ -like 'CN=*Part of Group Name*,*' }
The (...).memberOf syntax in PowerShell v3 and later is functionally equivalent to piping to Select-Object -ExpandProperty memberOf, so you could also write it this way:
Get-ADUser $user -Properties memberOf |
Select-Object -ExpandProperty memberOf |
Where-Object { $_ -like 'CN=*part of group name*,*' }
(The second variation would be required in PowerShell v2 which doesn't support the (...).memberOf "syntactic sugar.")
There's a cmdlet that works well for grabbing the group membership of a user. Try the following:
Get-ADPrincipalGroupMembership -Identity $user | Select -ExpandProperty Name | Select-String -Pattern 'Part of Group Name'

Adding all users to a AD group excluding a few ones using powershell

I have this doubt,
have to add every user in active directory to a group, but there are a few ones who dosen't have to be in this group,
I already know the information of this set of discriminated users..
so, there is a way to do a powershell command where i spicify this set of user and every user that dosen't match with this set would be added to the group?
i'm making a csv file whe is all the users by SamAccountName
Get-AdUser -Filter * | Select SamAccountName | Export-CSV c:\List.csv
, so i can add a second column with the name of the group, after that i was thinking to add a where clause in powershell to compare the SamAccountName with another csv with the set of discriminated users, but i don't know if that would work...
There is a simple way to do it?
I'd create a flat array with the exclusion then use it in the Where clause.
Something like:
$ExcludedUsers =
#(
"user1"
"user2"
#...
)
$GroupMembers = Get-AdUser -Filter * | Where-Object{ $ExcludedUsers -notcontains $_.samAccountName}
Add-ADGroupMember -Identity <GroupName> -Members $GroupMembers
If you are extracting the exclusions from a csv file you can use something like:
$ExcludedUsers = ( Import-Csv C:\ExcludedUsers.csv ).samAccountName
$GroupMembers = Get-AdUser -Filter * | Where-Object{ $ExcludedUsers -notcontains $_.samAccountName}
Add-ADGroupMember -Identity <GroupName> -Members $GroupMembers
$ExcludedUsers = #()
import-csv C:\ExcludedUsers.csv | ForEach-Object { $ExcludedUsers += $_.SamAccountName}
$GroupMembers = (Get-AdUser -Filter * | Where-Object{ $ExcludedUsers -notcontains $_.samAccountName})
Add-ADGroupMember -Identity GroupName -Members $GroupMembers
that's the code i use, if that helps anyone in the future.
thanks to Steve.

Filtering group memberships to copy from one user to another

I currently have working code that copies all group memberships of one user to another, taken from here:
Copy group membership from one user to another in AD
Get-ADuser $user_to_copy -Properties MemberOf | Select-Object -ExpandProperty MemberOf | Add-ADGroupMember -Members $user_name
I would like to add a filter which prevents groups that start with a number from being added.
For example:
123_Group - Would not be added to the new user.
Group_123 - Would be added to the new user.
I've been playing around with Where-Object but can't get it to work how I would like.
| Where-Object {$_.MemberOf -Match '[a-z]*'}
The groups have "CN=... etc." at the start which I've tried to account for as well but to no avail (no output errors, just not the output I need/expect). I'm not sure if I'm just making a mistake or should be attempting this another way.
Any help/advice is greatly appreciated.
Thank you.
Use .NET's Char.IsDigit method to check if the first character of the name is a numerical digit:
Get-ADuser $user_to_copy -Properties MemberOf `
| Select-Object -ExpandProperty MemberOf `
| Where-Object { -not [System.Char]::IsDigit($_[3]) } `
| Add-ADGroupMember -Members $user_name
I use $_[3] (the fourth character) since the memberOf attribute is a list of distinguishedName, which will all start with CN= followed by the name of the group.
Update: If you want to filter out groups that start with a certain string, use something like this:
$badstring = "Computer"
Get-ADuser $user_to_copy -Properties MemberOf `
| Select-Object -ExpandProperty MemberOf `
| Where-Object { -not $_.Substring(3).StartsWith($badstring) } `
| Add-ADGroupMember -Members $user_name

Target all users in two OU's and remove Distribution Lists

hoping to get a little help here – I looked around the site but didn’t see anything quite like this (please direct me if there IS and I missed it).
I need to incorporate a new step in our user offboarding process, which would remove them from any AD Distribution Lists. I would like to set this up as a scheduled task to run once a night against two OU’s where the inactivated user accounts can be found.
I’d like to run this by pointing it at the USERS instead of the OU where the Distro Lists live, because I suspect that we’ll ultimately get the request to remove these users from OTHER types of group as well.
This snippet will remove AD Distro Lists from a single user, but leave all other types of AD groups alone:
# GroupCategory 0 = Distro List
# GroupCategory 1 = Security Group
# GroupScope 0 = DomainLocal
# GroupScope 1 = Global
# GroupScope 2 = Universal
$user = "userlogon"
Get-ADPrincipalGroupMembership -Identity $user|
Where {$_.GroupCategory -eq 0} |
ForEach {Remove-ADPrincipalGroupMembership -Identity $user -MemberOf $_ -Confirm:$false}
THIS snippet will look at an OU and return some info (just my example for using a variable with -searchbase):
$OUs = 'OU=PendingDeletion,OU=Users,DC=Stuff,DC=Place,DC=net','OU=HoldForReview,OU=Users,DC=Stuff,DC=Place,DC=net'
$OU | ForEach {Get-ADGroup -Filter * -Properties ManagedBy -SearchBase $_ } |
Select Name, ManagedBy |
Sort -Property Name
Out-GridView
BUT – Does it hold together that in order to complete my objective, I would do something like this?! I'm a bit out of my depth here, any advice for a re-write is appreciated:
$OUs = 'OU=PendingDeletion,OU=Users,DC=Stuff,DC=Place,DC=net','OU=HoldForReview,OU=Users,DC=Stuff,DC=Place,DC=net'
$user = "*"
$OUs | ForEach {
Get-ADPrincipalGroupMembership -Identity $user|
Where {$_.GroupCategory -eq 0} |
ForEach {Remove-ADPrincipalGroupMembership -Identity $user -MemberOf $_ -Confirm:$false}
}
There’s always a couple of ways to do stuff in PoSh, so I’m sure there’s a less-complicated way to do the same thing. If anyone has a different approach please feel free to suggest an alternative.
Thanks for taking a look!
So it sounds like you need three loops.
First, you will need to loop over the OU list to get the Users. We'll store the user objects in $Users
$OUs = 'OU=PendingDeletion,OU=Users,DC=Stuff,DC=Place,DC=net','OU=HoldForReview,OU=Users,DC=Stuff,DC=Place,DC=net'
$Users = ForEach ($OU in $OUs) {
Get-ADUser -Filter * -SearchBase $OU
}
Next loop over the users to get the groups that you want to remove. Then loop over the groups to remove each one.
ForEach ($User in $Users) {
Get-ADPrincipalGroupMembership -Identity $user |
Where-Object {$_.GroupCategory -eq 0} |
ForEach-Object {
Remove-ADPrincipalGroupMembership -Identity $user -MemberOf $_
}
}
I think I'd take this a little differently, by getting the group membership of all users, then grouping by AD group, and processing each group that way. Seems like it would be a lot fewer calls to AD. So I'd start out getting all of the users, just like BenH, except I would include their MemberOf property. Then I'd build a list of potential groups and filter down to just the Distribution Lists. I'd make a Hashtable of those as the keys, and make the value an array of each user that is in that group. Then loop through that removing the value of each from the associated key.
$OUs = 'OU=PendingDeletion,OU=Users,DC=Stuff,DC=Place,DC=net','OU=HoldForReview,OU=Users,DC=Stuff,DC=Place,DC=net'
$Users = ForEach ($OU in $OUs) {
Get-ADUser -Filter * -SearchBase $OU -Properties MemberOf
}
$UsersByGroup = #{}
ForEach($Group in ($Users.MemberOf | Select -Unique | Get-ADGroup | Where{ $_.GroupCategory -eq 0 })) {
$UsersByGroup.Add($Group.DistinguishedName,($Users | Where{ $Group.DistinguishedName -in $_.MemberOf}))
}
$UsersByGroup.Keys | ForEach{
Remove-ADGroupMember -Identity $_ -Members $UsersByGroup[$_] -Confirm:$false
}

Copy group membership from one user to another in AD

Im tyring to build a script which will copy group memberships from one user to another in AD. Im trying to use powershell to automate this task. However im stuck while creating a check for the user. In other words when i copy group membership from one user to another i want to be able to run a check to see if the user is already a member of the group before adding them, bu doing this i can avoid errors which such as " this user is already a member of the group and cannot be added again" Any help or advice would be appreciated. Im using the following to script at the moment.
$copy = Read-host "Enter user to copy from"
$Sam = Read-host " Enter user to copy to"
Function Copymembership {
$members = Get-ADUser -Identity $copyp -Properties memberof
foreach ($groups in $members.memberof){
if ($members -notcontains $groups.sAMAccountname)
{Add-ADGroupMember -Identity $groups -Member $sam -ErrorAction SilentlyContinue
Write-Output $groups}
}
}
copymembership
Use Get-ADUser for both users. Then use the -notcontains operator to filter groups.
$CopyFromUser = Get-ADUser JSmith -prop MemberOf
$CopyToUser = Get-ADUser MAdams -prop MemberOf
$CopyFromUser.MemberOf | Where{$CopyToUser.MemberOf -notcontains $_} | Add-ADGroupMember -Member $CopyToUser
One line to get what the user member of.
Get-ADUser -Identity alan0 -Properties memberof | Select-Object -ExpandProperty memberof
One line to copy the membership from one user to another.
Get-ADUser -Identity <UserID> -Properties memberof | Select-Object -ExpandProperty memberof | Add-ADGroupMember -Members <New UserID>
Your code is too complicated for this idea. Not sure if it can be done without the import-Module AciveDirectory cmdlet.
It is much easer to do that when you import the ActiveDirectory tool and use the built-in cmdlet. Check my code:
# import the Active Directory module in order to be able to use get-ADuser and Add-AdGroupMembe cmdlet
import-Module ActiveDirectory
# enter login name of the first user
$copy = Read-host "Enter username to copy from: "
# enter login name of the second user
$paste = Read-host "Enter username to copy to: "
# copy-paste process. Get-ADuser membership | then selecting membership | and add it to the second user
get-ADuser -identity $copy -properties memberof | select-object memberof -expandproperty memberof | Add-AdGroupMember -Members $paste
Something like this should tell you if a group contains a specific member:
If ((Get-ADGroup "Domain Admins" -Properties Members).Members -Contains (Get-ADUser "AdminBob").DistinguishedName) {write-host "Yes"}
There might be something simpler but this was the first thing that came to mind.
param
(
[Parameter(Mandatory=$true)][string]$CopyFromUser,
[Parameter(Mandatory=$true)][string]$CopyToUser
)
$FromUserGroups = (Get-ADUser $CopyFromUser -Properties MemberOf).MemberOf
$CopyToUser = Get-ADUser $CopyToUser -Properties MemberOf
$FromUserGroups | Add-ADGroupMember -Members $CopyToUser
In case you want to have manual control on what groups are added, then this is perfect example for Out-GridView. Procedure is the same as explained by TheMadTechnician above, just before passing it to Add-ADGroupMember, you insert Out-GridView. You can even include group descriptions or other parameters.
$CopyFromUser = Get-ADUser JSmith -prop MemberOf
$CopyToUser = Get-ADUser MAdams -prop MemberOf
$MissingGroups = Compare-Object $CopyFromUser $CopyToUser -Property MemberOf | ? SideIndicator -eq '<='
$GroupsObj = $MissingGroups.MemberOf | Get-ADGroup –prop Description | Select Name,Description
$GroupsObj | Out-GridView -PassThru | Add-ADGroupMember -Member $CopyToUser
am trying build script to Copy group membership from one user to another in AD
i have one domain and 3 different subdomains, can you please check if there is anything in the script must be changed, because it doesn't work thanks
$From = Read-Host -Prompt "From User"
$to = Read-Host -Prompt "To User"
$CopyFromUser = Get-ADUser -Server "de.isringhausen.net" -Identity $From -Properties MemberOf
$Group = $CopyFromUser.MemberOf
$confirmation = Read-Host "Do you want to Copy Group Membership from $From to $to ? Press 'y' to Proceed or any key to Cancel"
if ($confirmation -eq 'y') {
$Group | Add-ADGroupMember -Members $to
clear
echo "($From) User's Group Memership has been Copied to User ($to)"
Pause
}
else {
Write-Host 'Task Cancelled'
}