We want to automate the process of removing the Individual user accounts from direct Local admin access

We want to automate the process of removing the individual user accounts who get directly added to Local admin access and not through an AD group. The problem is our AD is a mess, so there are many service accounts already added in local admin access which we dont want to remove because they will create problem. So we decided to use the employee id attribute to distinguish between users and service accounts and remove only the users and not local or service accounts. This is how my code looks like right now.

$Servers = "Get-Content "C:\scripts\joyservers.txt""
$results = @()

 

foreach ($computer in $Servers) {
    Invoke-Command -ComputerName $computer -ScriptBlock {
        $users = Get-LocalGroupMember -Group "administrators" | Where-Object { $_.objectclass -like 'User' -and $_.PrincipalSource -notlike "Local" -and $_.Name -notlike "*svc*" }

 

        foreach ($user in $users) {
            $userName = $user.Name
            $adUser = Get-ADUser -Identity $userName -Properties *
            if ($adUser.EmployeeId -ne $null) {
                $results += $adUser
            }
        }
    }
}

 

$results | Out-GridView

$results will give me the list of users it has selected for removal and later on we can add the | Remove-localgroupmember command to remove them.
The problem I am getting is that $results is giving me all the AD accounts i.e. user accounts and service accounts, whereas it should only give me user accounts. Dont know what I need to change in the script.

Joy,
Welcome to the forum. :wave:t3:

I’d create an AD group “ServerAdmins” or something similar, add the desired service accounts to that group and configure the GPO to be this group only to be in the servers adminsitrators group. :man_shrugging:t3:

Your code:
You don’t need a loop at all. The parameter -ComputerName of the cmdlet Invoke-Command takes a list / an array of computernames. :wink:

Regardless of that - you try to query your AD with a cmdlet from the ActiveDirectory PowerShell module from the remote computers/servers. Therefor you need to have the module installed on all these reomte computers/servers. I’d assume you don’t have this. :wink: :man_shrugging:t3:

1 Like

Thanks Olaf for your suggestion.
For the serveradmins group, every server has many different AD groups for different teams alongwith service accounts, thats why we are not considering this option as its not feasable.(Our AD is a big mess)
I am running the script from a domain controller on a server named gb-wat-svv-3828 which is up and running and has the ad ps module installed and its giving me this error:

"Unable to contact the server. This may be because this server does not exist, it is currently down, or it does not have the
Active Directory Web Services running.
+ CategoryInfo : ResourceUnavailable: (abcde\ab2098891:ADUser) [Get-ADUser], ADServerDownException
+ FullyQualifiedErrorId : ActiveDirectoryServer:0,Microsoft.ActiveDirectory.Management.Commands.GetADUser
+ PSComputerName : gb-wat-svv-3828

Unable to contact the server. This may be because this server does not exist, it is currently down, or it does not have the
Active Directory Web Services running.
+ CategoryInfo : ResourceUnavailable: (abcde\shoptest:ADUser) [Get-ADUser], ADServerDownException
+ FullyQualifiedErrorId : ActiveDirectoryServer:0,Microsoft.ActiveDirectory.Management.Commands.GetADUser
+ PSComputerName : gb-wat-svv-3828"

I’d recommend to change your approach a little bit. Start with collecting the raw data from the servers … something like this:

$computerList = Get-Content -Path "C:\scripts\joyservers.txt"

$LocalAdminGroupMemberList =
Invoke-Command -ComputerName $computerList -ScriptBlock {
    Get-LocalGroupMember -Group 'administrators' | 
        Where-Object {
            $_.objectclass -like 'user' -and 
            $_.PrincipalSource -notlike 'Local' -and 
            $_.Name -notlike '*svc*' 
        }
    } |
        Select-Object -Property PSComputerName, Name

$LocalAdminGroupMemberList | 
Out-GridView

That should give you the desired accounts in the variable ‘$LocalAdminGroupMemberList’. Now you can process this list with further steps to achieve what you need.

1 Like