Get Active Directory Object Attributes Export Result as CSV/XML


Gosh, took me the whole day to tidy up my Powershell script containing 5 cmdlets and submit it to Technet.

Download Link – http://gallery.technet.microsoft.com/Get-Active-Directory-f19ffa53

Pre-requisite Function
Note: This pre-requisite function is get the current script execution path for the Output Cmdlet.

#get execution path
$path = Get-ScriptDirectory

function Get-ScriptDirectory {

BEGIN {}

PROCESS {
    #extract my invoked command location
    $InvokedCommand = (Get-Variable MyInvocation -Scope 1).Value
    $path = Split-Path $InvokedCommand.MyCommand.Path
}

END { return $path }

} #end of #function Get-ScriptDirectory

 

Get-ADObjectProperty Cmdlet

function Get-ADObjectProperty {

<#   
.SYNOPSIS   
    Query Active Directory to return the object properties or attributes. Perform 
    network connectivity check on computer objects with active directory integrated 
    DNS service.
  
.DESCRIPTION   
    Allows the administrator to query the active directory using search filter for 
    active directory object and filter the result based on the object properties. 
    The cmdlet allows the administrator to query the active directory on computer 
    objects and perform network connectivity test against the active directory 
    integrated DNS service.

.PARAMETER Computer
    
    Specify a hostname for query.
    
.PARAMETER Filter
    
    Specify the search filter for query. To understand more about Search Filter, go to 
    http://msdn.microsoft.com/en-us/library/aa746475.aspx

.LINK
    Search Filter Syntax - http://msdn.microsoft.com/en-us/library/aa746475.aspx
         
.PARAMETER Properties
    
    Specify the object property or LDAP attributes for the result. To understand more 
    about Object Attributes, go to 
    http://msdn.microsoft.com/en-us/library/windows/desktop/ms675090(v=vs.85).aspx

.LINK
    All Object Attributes
    http://msdn.microsoft.com/en-us/library/windows/desktop/ms675090(v=vs.85).aspx

.PARAMETER TestNetwork
    
    Perform a test network connectivity on computer object only

.PARAMETER ExportCSV
    
    Export result into CSV format

.PARAMETER ExportXML
    
    Export result into XML format
        
.EXAMPLE
    Get-ADObjectProperty -filter "(&(objectCategory=User)(name=Ryen Tang))"
    
    This query the Active Directory for a User Object name "Ryen Tang" and return the 
    object properties sliently. You will not see any output on the powershell console

.EXAMPLE    
    Get-ADObjectProperty -filter "(&(objectCategory=Computer)(name=HOSTNAME)(operatingSystem=Windows Server 2008*))" -verbose
  
    This query the Active Directory for a Windows Server 2008 operating system Computer 
    Object Name "HOSTNAME" and return the object properties on the powershell console 
    in verbose

.EXAMPLE     
    Get-ADObjectProperty -verbose
    
    This query the Active Directory on the localhost and return the object properties on 
    the powershell console in verbose

.EXAMPLE
    Get-ADObjectProperty -filter "(&(objectCategory=Computer)(operatingSystem=Windows Server 2008*))" -testnetwork
    
    This allows the administrator to perform a query on the active directory in search 
    for all the computers running on the Windows Server 2008 operating system and 
    perform a test on their network connectivity towards the active directory integrated
    DNS service.

.NOTES   
    Author: Ryen Kia Zhi Tang
    Date  : 15/07/2012
    Blog  : ryentang.wordpress.com
      
#>

[CmdletBinding(
    SupportsShouldProcess=$True,
    ConfirmImpact='High')]
        
# define command parameters
param
(
    [Parameter(
        Mandatory=$False,
        ValueFromPipeline=$True,
        ValueFromPipelineByPropertyName=$True)]
        


    [string] $Filter = "",
    [string[]] $Properties = "",
    [string] $Computer = "",
    [switch] $TestNetwork,
    [switch] $ExportCSV,
    [switch] $ExportXML
)

BEGIN{

    if($computer -eq "") { $computer = $env:computername }

}

PROCESS{
    #create a result array
    $result = @()
    
    if($filter -ne "") {

        #execute query
        $items = Query-ActiveDirectory($filter)

        #verify if the queried items are empty
        if($items -ne 0) {
            
            #execute Expand-ADOProperty on Query-ActiveDirectory returned result in $items
            $object = Expand-ADOProperty $items $properties
                
            #set counter to zero
            $counter = 0
            
            #validate if -Test-Network parameter is defined
            if($TestNetwork) {
            
                #for each item from the queried items
                foreach($item in $object) {

                    #validate $item.name is not null
                    if($item.name -ne $null) {
                    
                        [String] $hostname = $item.name
                        
                        #validate if $item is a computer object
                        if($item.operatingsystem -ne $null) {
                        
                            #execute network connectivity test process
                            $object = Test-Network $hostname $counter

                            if($PSBoundParameters['Verbose']) { $object | format-list }
                            
                            #dump the object to result
                            $result += $object
                        
                        }else{
                            
                            $object | Add-Member -MemberType noteproperty -Name "System Name" -value "$hostname is not a computer object. Abort network test."
                            
                            if($PSBoundParameters['Verbose']) { $object | format-list }
                            
                            $result += $object
                            
                        } #end of #validate if $item is a computer object
                    
                    } #end of #validate $item is not null
                    
                    #increment counter
                    $counter ++
            
                } #end of #for each item from the queried items    

                
            }else{
                
                if($PSBoundParameters['Verbose']) { $object | format-list }
                            
                $result += $object
                
            } #end of #validate if -Test-Network parameter is defined
            
        }else{
            
            #create an object to store data
            $object = New-Object PSObject
            
            $object | Add-Member -MemberType noteproperty -Name "Query Result" -value "Empty"
            
            if($PSBoundParameters['Verbose']) { $object | format-list }
            
            $result += $object
            
        } #end of #verify if the queried items are empty
        
    }else{
        
        if($TestNetwork) { 
        
            $object = Test-Network $computer $counter
        
        }elseif($PSBoundParameters['Verbose']) {
            
            $filter = "(&(objectCategory=Computer)(name=$computer))"

            #execute query
            $items = Query-ActiveDirectory($filter)
            
            #execute expand property
            $object = Expand-ADOProperty $items $properties

        } #end of #elseif($verbose)
        
        if($PSBoundParameters['Verbose']) { $object | format-list }
        
        $result = $object

    }

    #dump result format
    if($exportcsv) {

        #dump result in csv
        output "csv" $result $path
           
    }elseif($exportxml) {
        
        #dump result in xml        

        output "xml" $result $path
           
    }
    
} #end of #PROCESS{}

END{}

} #end of #function Get-ADObjectProperty

 

Query-ActiveDirectory Cmdlet

function Query-ActiveDirectory {

<#   
.SYNOPSIS   
    Query Active Directory to return an array of object properties or attributes.
  
.DESCRIPTION   
    Allows the administrator to query the active directory using search filter for an 
    array of active directory objects.
   
.PARAMETER Filter
    
    Specify the search filter for query. To understand more about Search Filter, go to 
    http://msdn.microsoft.com/en-us/library/aa746475.aspx

.LINK
    Search Filter Syntax - http://msdn.microsoft.com/en-us/library/aa746475.aspx
        
.EXAMPLE
    Query-ActiveDirectory -filter "(&(objectCategory=User)(name=Ryen Tang))"
    
    This query the Active Directory for a User Object name "Ryen Tang" and return the 
    array of object properties sliently. You will not see any output on the powershell 
    console.

.INPUT
    The filter syntax string can be piped to the function or script or cmdlet.

.OUTPUT
    The .NET Framework type of the objects that the cmdlet returns. There is no visible 
    output for this cmdlet except for an array of objects from active directory.
    
.NOTES   
    Author: Ryen Tang
    Date  : 15/07/2012
    Blog  : ryentang.blogspot.com
    Version : 1.0
    
#>

[CmdletBinding(
    SupportsShouldProcess=$True,
    ConfirmImpact='High')]
        
#define command parameters
param(
    
    [Parameter(
        Mandatory=$True,
        ValueFromPipeline=$True,
        ValueFromPipelineByPropertyName=$True)]    
    
    [string] $filter
)

BEGIN {}

PROCESS {

    #create directory entry object
    $objDomain = New-Object System.DirectoryServices.DirectoryEntry

    #create directory searcher object
    $objSearcher = New-Object System.DirectoryServices.DirectorySearcher
    $objSearcher.SearchRoot = $objDomain

    #input custom filter
    $objSearcher.Filter = ($filter)

    #get properties
    $propertieslist = "*"
    foreach ($i in $propertieslist){$objSearcher.PropertiesToLoad.Add($i)}

}

END { return $objSearcher.FindAll() }

} #end of function Query-ActiveDirectory

 

Output Cmdlet

function Output {

<#   
.SYNOPSIS   
    Output an object into either CSV or XML file format.
  
.DESCRIPTION   
    Output an object into either CSV or XML file format at the script execution folder location.

.PARAMETER Option
    
    Specify CSV or XML file format
    
.PARAMETER Object
    
    Specify the Object to be parsed

.EXAMPLE
    Output "CSV" (Expand-ADOProperty (Query-ActiveDirectory -filter "(&(objectCategory=User)(name=Ryen*))")) Get-ScriptDirectory
    
    This query the Active Directory for a User Object name "Ryen Tang" and return the 
    object properties sliently. You will not see any output on the powershell console 
    but you will have an CSV file in script execution folder location.

.EXAMPLE
    Output "XML" (Expand-ADOProperty (Query-ActiveDirectory -filter "(&(objectCategory=User)(name=Ryen*))")) Get-ScriptDirectory
    
    This query the Active Directory for a User Object name "Ryen Tang" and return the 
    object properties sliently. You will  not see any output on the powershell console 
    but you will have an XML file in script execution folder location.
     
.NOTES   
    Author: Ryen Kia Zhi Tang
    Date  : 15/07/2012
    Blog  : ryentang.wordpress.com
    Version : 1.0
    
#>

[CmdletBinding(
    SupportsShouldProcess=$True,
    ConfirmImpact='High')]
        
#define command parameters
param(
    
    [Parameter(
        Mandatory=$True,
        ValueFromPipeline=$True,
        ValueFromPipelineByPropertyName=$True)]    
    
    [string] $option,
    [object] $object,
    [string] $path
)

BEGIN {
    #get timestamp
    $timestamp = Get-Date -format yyyyMMdd-HHmmss
}

PROCESS {
    switch($option) {
        "csv" {

            #export as csv
            $object | export-csv "ComputerObject-Test-Network-Result-$timestamp.csv" -NoTypeInformation -NoClobber

            #construct file path
            $filepath = Join-Path ($path) "ComputerObject-Test-Network-Result-$timestamp.csv"

            #display exported CSV file location
            write-verbose "Exported CSV is located at $filepath"
        }
        
        "xml" {
            
            #export as csv
            $object | export-clixml "ComputerObject-Test-Network-Result-$timestamp.xml" -NoClobber

            #construct file path
            $filepath = Join-Path ($path) "ComputerObject-Test-Network-Result-$timestamp.xml"

            #display exported CSV file location
            write-verbose "Exported XML is located at $filepath"
        }
        
    }
}#end of PROCESS {}

END {}

} #end of #function Output

 

Test-Network Cmdlet

function Test-Network {

<#   
.SYNOPSIS   
    Perform Network Connectivity Test
  
.DESCRIPTION   
    Allows the administrator to perform network connectivity test on localhost or other 
    hosts with DNS Forward Lookup Test, DNS Reverse Lookup Test and Ping Test.

.PARAMETER Hostname
    
    Specify Hostname to be tested

.EXAMPLE
    Test-Network Hostname
    
    This execute the network connectivity test on the hostname.

.EXAMPLE
    Test-Network Localhost
    
    This execute the network connectivity test on the localhost.
     
.NOTES   
    Author: Ryen Kia Zhi Tang
    Date  : 15/07/2012
    Blog  : ryentang.wordpress.com
    Version : 1.0
    
#>

[CmdletBinding(
    SupportsShouldProcess=$True,
    ConfirmImpact='High')]
        
# define command parameters
param(
    
    [Parameter(
        Mandatory=$True,
        ValueFromPipeline=$True,
        ValueFromPipelineByPropertyName=$True)]    
    
    [string] $hostname,
    
    [Parameter(
        Mandatory=$False,
        ValueFromPipeline=$True,
        ValueFromPipelineByPropertyName=$True)] 
    [int] $counter
)
    
BEGIN {}

PROCESS {
    
    #create an object to store data
    $object = New-Object PSObject
        
    #verify if $hostname is empty    
    if($hostname -ne "") {

        $object | Add-Member -MemberType noteproperty -Name "Query Result" -value $counter
        $object | Add-Member -MemberType noteproperty -Name "System Name" -value $hostname
        
        try {
            
            #test DNS Forward Lookup
            if([system.net.Dns]::GetHostAddresses("$hostname")) { 

                #get IP addresses
                [String] $ipaddresses = [system.net.Dns]::GetHostAddresses("$hostname") | Select-Object IPAddress -expandproperty IPAddressToString
                
                #if IP address is not null
                if($ipaddresses -ne "") {

                    try {
                        
                        #split multiple ip addresses
                        $ipaddress = $ipaddresses.Split(" ",[StringSplitOptions]'RemoveEmptyEntries')
                        
                        #for each ip address                       
                        foreach($entry in $ipaddress) {
                        
                            #test DNS Reverse Lookup
                            if([system.net.Dns]::GetHostEntry("$entry")) { 
                                
                                #get hostname
                                [String] $hostname = [system.net.Dns]::GetHostEntry("$entry") | Select-Object Hostname -expandproperty Hostname
                                
                                #verify if $entry is IPV6
                                if($entry.contains("::")) {
                                
                                    $object | Add-Member -MemberType noteproperty -Name "DNS Reverse Lookup IPV6 Address" -value $entry -force
                                    
                                }else{
                                
                                    if(($object | Get-Member -Name "DNS Reverse Lookup IPV6 Address") -eq $null) {
                                        
                                        $object | Add-Member -MemberType noteproperty -Name "DNS Reverse Lookup IPV6 Address" -value "" -force
                                    
                                    }
                                    
                                } #end of #verify if $entry is IPV6
                                
                                #verify if $entry is IPV4
                                if($entry.contains(".")) {
                                
                                    $object | Add-Member -MemberType noteproperty -Name "DNS Reverse Lookup IPV4 Address" -value $entry -force
                                  
                                }else{
                                
                                    if(($object | Get-Member -Name "DNS Reverse Lookup IPV4 Address") -eq $null) {
                                        
                                        $object | Add-Member -MemberType noteproperty -Name "DNS Reverse Lookup IPV4 Address" -value "" -force
                                        
                                    }
                                    
                                } #end of #verify if $entry is IPV4
                                
                            } #end of #test DNS Reverse Lookup
                        
                        } #end of #for each ip address
                                    
                    }catch{
                    
                        if($entry.contains(":")) {
                        
                            $object | Add-Member -MemberType noteproperty -Name "DNS Reverse Lookup IPV6 Address" -value $_.ToString()

                        }
                        if($entry.contains(".")) {
                            
                            $object | Add-Member -MemberType noteproperty -Name "DNS Reverse Lookup IPV4 Address" -value $_.ToString()

                        }
                    }
                    
                } #end of #if IP address is not null

                $object | Add-Member -MemberType noteproperty -Name "DNS Forward Lookup IP Address" -value $hostname
                
            } #end of #test DNS Forward Lookup
            
        }catch{
            
            #write error exception
            $object | Add-Member -MemberType noteproperty -Name "DNS Forward Lookup IP Address" -value $_.ToString()
            
        }
        
        # test network connectivity
        if(test-connection -computername $hostname -quiet) {
            
            $object | Add-Member -MemberType noteproperty -Name "Ping" -value "Passed"
        
        }else{
            
            $object | Add-Member -MemberType noteproperty -Name "Ping" -value "Failed"
       
        }
        
    }else{
    
        $object | Add-Member -MemberType noteproperty -Name "Query Result" -value "Empty"
    
    } #end of #verify if $hostname is empty

} #end of #PROCESS {}
    
END { return $object }
 
} #end of #function Test-Network

Expand-ADOProperty Cmdlet

function Expand-ADOProperty {

<#   
.SYNOPSIS   
    Expand the object properties or attributes
  
.DESCRIPTION   
    Allows the administrator to expand an object properties or attributes or filter the 
    properties or attributes for easier viewing.

.PARAMETER Object
    
    Specify the object to be parsed

.PARAMETER Properties
    
    Specify properties or attributes to be expanded
    
.EXAMPLE    
    Expand-ADOProperty (Query-ActiveDirectory "(&(objectCategory=computer)(name=HOSTNAME))")
    
    This query the Active Directory for a specific Computer Object Name "HOSTNAME" and 
    return an array of object properties or attributes output on the powershell console

.EXAMPLE
    Expand-ADOProperty (Query-ActiveDirectory "(&(objectCategory=user)(name=Ryen*))")
    
    This query the Active Directory for a specific User Object Name "Ryen" with a 
    wildcard and return an array of object properties or attributes output on the 
    powershell console
     
.NOTES   
    Author  : Ryen Kia Zhi Tang
    Date    : 15/07/2012
    Blog    : ryentang.wordpress.com
    Version : 2.0
      
#>

[CmdletBinding(
    SupportsShouldProcess=$True,
    ConfirmImpact='High')]

     
# define command parameters
param(
    
    [Parameter(
        Mandatory=$True,
        ValueFromPipeline=$True,
        ValueFromPipelineByPropertyName=$True)]
        
    [object] $object,
    
    [Parameter(
        Mandatory=$False,
        ValueFromPipeline=$True,
        ValueFromPipelineByPropertyName=$True)]    
    
    [string[]] $properties = ""
)

BEGIN{}

PROCESS{

    $items = $object

    #create a result array
    $result = @()
    
    #set counter to zero
    $counter = 0
                
    #for each item from the queried items
    foreach ($item in $items) {

        #create an object to store data
        $object = New-Object PSObject
        
        $item = $item.Properties
        
        #validate $item is not null
        if($item -ne $null) {

            #increment counter
            $counter ++
                       
            $object | Add-Member -MemberType noteproperty -Name "Query Result" -value "$counter"

            if($properties -ne $null) {

                    #for each property in -properties parameter
                    foreach($property in $properties) {

                            $value = [string] $item.$property
                            $object | Add-Member -MemberType noteproperty -Name "$property" -value "$value"

                    } #end of #for each property in -properties parameter

            }else{
                        
                    $propertynames = $item | Select -ExpandProperty PropertyNames
                    
                    #for each property from the entire properties
                    foreach($propertyname in $propertynames) {
                        
                            $value = [string] $item.$propertyname
                            $object | Add-Member -MemberType noteproperty -Name "$propertyname" -value "$value"

                    } #end of #for each property from the entire properties

            }
            
            $result += $object        
        
        } #end of #validate $item is not null
        
        
        
    } #end of #for each item from the queried items

} #end of PROCESS {}

END { return $result }
    
} #end of #function Expand-ADOProperty
Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s