Check Every group in AD and get the names of users where Display name is the same for more than 1.

Hi,

Check Every group in AD and get the names of users where Display name is the same for more than 1.
I have 100's of groups scattered in root and 3 child Domains. I want help with a script that can query all groups and get the names of users where the user is listed more than once. They can be contact or user account.

Regards
Sharath
LVL 11
bsharathAsked:
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

x
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

Chris DentPowerShell DeveloperCommented:

This is really quite a complex script.

It's as efficient as I can make it but it may still absorb a large amount of your system RAM when it creates the index.

Chris
# This must be a Global Catalog
$GC = Connect-QADService "server.domain.local" -UseGlobalCatalog
# This must be the Root Domain Naming Context
$RootDomain = "DC=root,DC=domain"

# Create an index of user and contact objects by Display Name and Distinguished Name

$ObjectDNCache = @{}
$ObjectNameCache = @{}
Get-QADObject -SearchRoot $RootDomain `
    -Connection $GC -LdapFilter "(&(objectCategory=person)(displayName=*))" -SizeLimit 0 | %{

  If (!$ObjectNameCache.Contains($_.DisplayName))
  {
    $ObjectNameCache.Add($_.DisplayName, @($_.DN))
  }
  Else
  {
    $ObjectNameCache.$($_.DisplayName) += $_.DN
  }

  $ObjectDNCache.Add($_.DN, $_.DisplayName)
}

# Get all groups from the Global Catalog

Get-QADGroup -SearchRoot $RootDomain `
    -Connection $GC -SizeLimit 0 | %{

  $GroupDN = $_.DN

  # Check this group for duplicate members

  $Members = $_.member | %{ $_ | Select-Object @{n='Name';e={ $ObjectDNCache.$_ }} | ?{ $_.Name -ne $Null } }

  $Members | Group-Object Name | ?{ $_.Count -gt 1 } | %{
    $Name = $_.Name
    $ObjectNameCache.$Name | %{
      $_ | Select-Object `
        @{n='GroupDN';e={ $GroupDN }},
        @{n='ObjectDisplayName';e={ $Name }}, 
        @{n='ObjectDN';e={ $_ }}
    }
  }
}

Open in new window

0
bsharathAuthor Commented:
Thanks Chris
Just to confirm. the display name is checked between the user and User and Contact and Contact and user and Contact within each group and results populated right
Hope you are checking with display name as my contacts show as just when seen when we go to properties in display name the name is right
0
Chris DentPowerShell DeveloperCommented:

It compares display names between group members. It doesn't care if the object is a group, or user, or contact.

The output shows the group names, and all matches associated with a given displayName.

If a displayName is not set the object will be ignored and will not be compared.

Chris
0
Webinar: Miercom Evaluates Wi-Fi Security

It's not just about Wi-Fi connectivity anymore. A wireless security breach can cost your business large amounts of time, trouble, and expense. Plus, hear first-hand from Miercom how WatchGuard's Wi-Fi security stacks up against the competition in our upcoming webinar!

Chris DentPowerShell DeveloperCommented:

This may get you around the time-out message you suffer from.

Chris
# This must be a Global Catalog
$GC = Connect-QADService "server.domain.local" -UseGlobalCatalog
# This must be the Root Domain Naming Context
$RootDomain = "DC=root,DC=domain"

# Create an index of user and contact objects by Display Name and Distinguished Name

$ObjectDNCache = @{}
$ObjectNameCache = @{}
Get-QADObject -SearchRoot $RootDomain `
    -Connection $GC -LdapFilter "(&(objectCategory=person)(displayName=*))" -SizeLimit 0 | %{

  If (!$ObjectNameCache.Contains($_.DisplayName))
  {
    $ObjectNameCache.Add($_.DisplayName, @($_.DN))
  }
  Else
  {
    $ObjectNameCache.$($_.DisplayName) += $_.DN
  }

  $ObjectDNCache.Add($_.DN, $_.DisplayName)
}

# Get groups from the global catalog for each domain

$RootDSE = [ADSI]"LDAP://RootDSE"
$DsSearchRoot = [ADSI]"LDAP://CN=Partitions,$($RootDSE.Get('configurationNamingContext'))"
$DsLdapFilter = "(&(objectCategory=crossRef)(nETBIOSName=*))"
(New-Object DirectoryServices.DirectorySearcher($DsSearchRoot, $DsLdapFilter)).FindAll() | %{

  # Set the search root to a single domain
  $SearchRoot = $_.Properties["ncname"][0]
  # Set the search host to the domain name
  $Service = $_.Properties["dnsroot"][0]

  Get-QADGroup -SearchRoot $SearchRoot `
      -Service $Service -SizeLimit 0 | %{

    $GroupDN = $_.DN

    # Check this group for duplicate members

    $Members = $_.member | %{ $_ | Select-Object @{n='Name';e={ $ObjectDNCache.$_ }} | ?{ $_.Name -ne $Null } }

    $Members | Group-Object Name | ?{ $_.Count -gt 1 } | %{
      $Name = $_.Name
      $ObjectNameCache.$Name | %{
        $_ | Select-Object `
          @{n='GroupDN';e={ $GroupDN }},
          @{n='ObjectDisplayName';e={ $Name }}, 
          @{n='ObjectDN';e={ $_ }}
      }
    }
  }
}

Open in new window

0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
bsharathAuthor Commented:
Script ran with no errors
But no output as well.
Does it store in any file?
0
Chris DentPowerShell DeveloperCommented:

Hmm I did wonder if it might break that. That puts us back to the original script, and the problem it bumped into before.

The only way I can make it more efficient is if I implement a directory search myself rather than using Get-QADGroup. That would have to use System.DirectoryServices.Protocols to gain anything, and I think that will just be too hard to support remotely.

Chris
0
bsharathAuthor Commented:
Thanks Chris...
For now i think shall dump each group members into txt files copy them into excel and then check for Duplicates.
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Programming Languages-Other

From novice to tech pro — start learning today.