Link to home
Start Free TrialLog in
Avatar of tobstah
tobstahFlag for United States of America

asked on

vb script to find empty ad groups

Can someone share a vb script that will generate a list of groups with zero user objects as members active directory groups from a 2000 domain? thanks.
Avatar of RickSheikh
RickSheikh
Flag of United States of America image

This is where I love PowerShell over VB (see http://tinyurl.com/PoshQAD) if interested. Below one liner can get what you want.

Get-QADGroup -Empty $true -sizelimit 0
Avatar of Mike Kline
I'll  throw in the adfind/LDAP method
http://www.joeware.net/freetools/tools/adfind/index.htm
adfind -default -f  "&(objectcategory=group)(!member=*)"  name member
member should not return/output any results but I added it to double check the query.
Thanks
Mike
 

You'll probably find Domain Users included in the output from the queries above (unless you changed the Primary Group setting for anyone). That's because of how membership for that group is stored. So, if it is included, it's not an error and you can just ignore it.

Chris
Avatar of tobstah

ASKER

Unfortunately powershell does not work with windows 2000 AD.

It won't install on the server, but it will run against the directory if you have an XP workstation (or a 2003 server somewhere).

Still, ADFind will, or the query Mike wrote can be used in AD Users and Computers if you prefer. Either in a Saved Query or in the Find option, in both cases, choose Custom Search, then use the Advanced tab and paste the query into there.

Chris
ASKER CERTIFIED SOLUTION
Avatar of rlandquist
rlandquist
Flag of United States of America image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of tobstah

ASKER

Nice script. What about putting the output into an excel spreadsheet with the group name, parent OU, and LDAP path in separate cells? Here is kinda what I have in mind at the bottom...

 
 
 
'Define Constants
Const ADS_SCOPE_SUBTREE = 2 ' Search target object and all sub levels
 
'Set Variables
DQ = Chr(34) 'Double Quote
 
'Create Objects
Set objShell = CreateObject("Wscript.Shell")
 
'Verifies script was run using CSCRIPT, and if not relauches it using CSCRIPT
If Not WScript.FullName = WScript.Path & "\cscript.exe" Then
        objShell.Popup "Launched using wscript. Relaunching...", 5, "WSCRIPT"
        objShell.Run "cmd.exe /k " & WScript.Path & "\cscript.exe //NOLOGO " & _
        DQ & WScript.scriptFullName & DQ, 1, False
        WScript.Quit 0
End If
 
'Construct an ADsPath to the Current Domain with rootDSE
Set objRootDSE = GetObject("LDAP://rootDSE")
strADsPath = "LDAP://" & objRootDSE.Get("defaultNamingContext")
 
'Connect to Active Directory
Set objConnection = CreateObject("ADODB.Connection")
Set objCommand = CreateObject("ADODB.Command")
objConnection.Provider = "ADsDSOObject"
objConnection.Open "Active Directory Provider"
Set objCommand.ActiveConnection = objConnection
objCommand.Properties("Page Size") = 1000
objCommand.Properties("Searchscope") = ADS_SCOPE_SUBTREE
 
objCommand.CommandText = "SELECT ADsPath,member FROM '" & strADsPath & _
"'" & " WHERE objectClass='group'"
Set objRecordSet = objCommand.Execute
 
If objRecordSet.EOF Then
        WScript.echo "Error, no groups found"
        WScript.quit
Else
        WScript.Echo "List of empty groups"
        WScript.Echo "============================================================="
        objRecordSet.MoveFirst
        Do Until objRecordSet.EOF
                strGroupName = objRecordSet.Fields("ADsPath").Value
                arrMembers = objRecordSet.Fields("member").Value
                If IsNull(arrMembers) Then
                        WScript.Echo strGroupName
                        
                End If
                objRecordSet.MoveNext
        Loop
End If
 
WScript.Echo "Script has finished"
 
 
 
 
________________________
 
'constant for incrementing the line in the excel spreadsheet.
k=2
 
strExcelPath = InputBox ("Please enter the path to save file to: ", "File path", "F:\")
strExcelPath = strExcelPath & "Printers_" & strComputer & ".xls"
 
' Bind to Excel object.
On Error Resume Next
Set objExcel = CreateObject("Excel.Application")
If Err.Number <> 0 Then
  On Error GoTo 0
  Wscript.Echo "Excel application not found."
  Wscript.Quit
End If
 
' Create a new workbook.
objExcel.Workbooks.Add
 
'populate the row with this printer's data
objSheet.Cells(k, 1).Value = strGroupName
objSheet.Cells(k, 2).Value = strGroupName.dn
 
'move down one line
k = k + 1

Open in new window

Avatar of tobstah

ASKER

Incidentally I have *hundreds* of empty groups and dozens of nested OUs to identify and remove.
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of tobstah

ASKER

Code comments are good for us newbs.

Ahh true, sorry, bit of a rush had to go and cook dinner ;)

Chris
' Create an object to connect to AD
Dim objConnection : Set objConnection = CreateObject("ADODB.Connection")
objConnection.Provider = "ADsDSOObject"
objConnection.Open "Active Directory Provider"
 
' Create the Command object
Dim objCommand : Set objCommand = CreateObject("ADODB.Command")
Set objCommand.ActiveConnection = objConnection
' Enable Paging. Limited to 1000 results otherwise, this returns 1000 per page
objCommand.Properties("Page Size") = 1000
 
' Connect to RootDSE, useful to get configuration information for the current forest
Dim objRootDSE : Set objRootDSE = GetObject("LDAP://RootDSE")
' Create a command to search AD. defaultNamingContext is the current domain in the form 
' DC=domain,DC=com.
objCommand.CommandText = "<LDAP://" & objRootDSE.Get("defaultNamingContext") & ">;" & _
  "(&(objectClass=group)(!member=*));name,distinguishedName;subtree"
 
' Execute the command
Dim objRecordSet : Set objRecordSet = objCommand.Execute
 
' Create the file system object so we can work with files
Dim objFSO : Set objFSO = CreateObject("Scripting.FileSystemObject")
' Create a text file called EmptyGroups.csv. Open for Writing (2) and overwrite the file 
' if it exists (True). Use system default text formatting (options include ASCII and Unicode)
Dim objFile : Set objFile = objFSO.OpenTextFile("EmptyGroups.csv", 2, True, 0)
' Write a comma delimited header line to the file
objFile.WriteLine "Name,DN"
 
' Begin looping through the results
Do Until objRecordSet.EOF
  ' Write the group name and distinguishedName to the file in the following format:
  ' "name","CN=name,OU=somewhere,DC=domain,DC=com"
  ' Note that doubling up quotes escapes the script meaning, "" represents a single quote in a 
  ' string.
  objFile.WriteLine """" & objRecordSet.Fields("name").Value & """,""" & _
    objRecordSet.Fields("distinguishedName").Value & """"
 
  objRecordSet.MoveNext
Loop

Open in new window