Inventorying Exchange custom attribute (extensionAttribute#\CustomAttribute#) usage within your environment

My team recently fielded a request for an unused Exchange custom attribute to use for various automation tasks around AD user groups. Since multiple teams at my company have access to various types of AD objects, we decided to do a quick inventory of the usage of those various attributes. Some quick background on those attributes

In total there are 50 total attributes that Exchange uses to extend the AD schema:

  • extensionAttribute1 to extensionAttribute15 (String)
  • msExchExtensionAttribute16 to msExchExtensionAttribute45 (String)
  • msExchExtensionCustomAttribute1 to msExchExtensionCustomAttribute5 (String: Multi-Valued)

MS recommends sticking to 1-15 and the 5 extension ones. 16-45 might be used for future Exchange features, but I personally haven’t seen this.

in Exchange Online, the data from extensionAttribute# are stored as CustomAttribute#. The multi valued ones also get synced up as ExtensionCustomAttribute#

Normally, in an Exchange Hybrid environment, Azure AD connect will sync the attributes that appear in Exchange Online. You can also extend the rest of the extension attributes as well as any locally created AD attributes.

The following PowerShell code will generate a list of which objects have those 50 attributes filled

$AttributeTable = @{
    extensionAttribute = 1..15
    msExchExtensionAttribute = 16..45
    msExchExtensionCustomAttribute = 1..5

$ExtensionEntries = [System.Collections.ArrayList]@()

foreach ($Attribute in $AttributeTable.GetEnumerator()) {
    [String]$AttributeBase = $Attribute.Name
    $Attribute.value | 
        ForEach-Object {
            $CurrenntAttribute = "$AttributeBase$_"
            [array]$current = Get-ADObject -Filter "$CurrenntAttribute -like '*'" -Properties $CurrenntAttribute | Select-object Name, ObjectClass, $CurrenntAttribute, @{N='FilledAttribute';E={$CurrenntAttribute}}
            if ($current.count -ne 0) {

$ExtensionEntries | group-object FilledAttribute | Sort-object Name | Select-object Name, Count

The direct output will be like so:

Name                            Count
----                            -----
extensionAttribute1              1115
extensionAttribute2               842
extensionAttribute3               925
extensionAttribute4               799
extensionAttribute5               603
extensionAttribute9                63
extensionAttribute10              580
extensionAttribute12                1
extensionAttribute13               17
extensionAttribute14              235
extensionAttribute15              110
msExchExtensionAttribute16      17047
msExchExtensionAttribute17         72
msExchExtensionAttribute45          1
msExchExtensionCustomAttribute1     3

But you can also sort by ObjectClass, or any other properties you would like to add as part of the Get-ADObject call

About mell9185

IT proffesional. Tech, video game, anime, and punk aficionado.
This entry was posted in Uncategorized and tagged , , . Bookmark the permalink.

Leave a Reply