We use cookies to improve your experience.
By your continued use of this site you accept such use.
For more details please see our privacy policy and cookies policy.

Script Repository

Microsoft 365 licenses assigned to dynamic distribution list members

The script creates a CSV-formatted report on licenses assigned to members of a dynamic distribution list.

To generate such a report on request, you can create a custom command that runs the script on Ms-Exch-Dynamic-Distribution-List objects. For this purpose, on Step 2 of the Create Custom Command wizard, select Show all object types and Ms-Exch-Dynamic-Distribution-List.

Parameters:

  • $exchangeServer - Specifies the fully qualified domain name (FQDN) of your Exchange Server.
  • $csvFilePath - Specifies a full path to the CSV file containing the report.
  • $propertiesToExport - Specifies LDAP names of properties of the members to to include in the report.
Edit Remove
PowerShell
$exchangeServer = "exchangeserver.domain.com" # TODO: modify me
$csvFilePath = "\\SERVER\share\members.csv" # TODO: modify me
$propertiesToExport = @("Name", "Description", "Department", "mail") # TODO: modify me

try
{
    # Create a remote PowerShell session to the Exchange Server
    $session = New-PSSession -configurationname Microsoft.Exchange -connectionURI http://$exchangeServer/PowerShell
    Import-PSSession $session -DisableNameChecking -AllowClobber
    
    # Get Dynamic Distribution Group
    $group = Get-DynamicDistributionGroup -Identity "%distinguishedName%"
    
    # Get members
    $members = Get-Recipient -RecipientPreviewFilter $group.RecipientFilter -OrganizationalUnit $group.RecipientContainer
    
    # Build search filter to find all members in AD
    $filter = New-Object "System.Text.StringBuilder"
    [void]$filter.Append("(|")
    
    foreach ($member in $members)
    {
        $guid = [Guid]$member.Guid
        [void]$filter.Append([Softerra.Adaxes.Ldap.FilterBuilder]::Create("objectGuid", $guid))
    }
    
    [void]$filter.Append(")")
}
finally
{
    # Release resources
    if ($session) { Remove-PSSession $session }
}

# Find members in AD
$domainName = $Context.GetObjectDomain("%distinguishedName%")
$searcher = $Context.BindToObject("Adaxes://$domainName/RootDSE")
$searcher.SearchFilter = $filter.ToString()
$searcher.PageSize = 500
$searcher.SetPropertiesToLoad($propertiesToExport)

try
{
    $searchResultIterator = $searcher.ExecuteSearch()
    $searchResults = $searchResultIterator.FetchAll()
        
    $records = @()
    foreach ($searchResult in $searchResults)
    {
        $record = New-Object PSObject
        foreach ($propertyName in $propertiesToExport)
        {
            $record | Add-Member -Name $propertyName -Value $searchResult.Properties[$propertyName].Value -MemberType NoteProperty
        }

        $record | Add-Member -Name "IsLicensed" -Value $NULL -MemberType NoteProperty
        
        # Bind to member
        $member = $Context.BindToObject($searchResult.AdsPath)

        if ($member.Class -eq "User")
        {
            $isLicensed = $False
            try
            {
                # Get Microsoft 365 properties
                $microsoft365Properties = $member.GetOffice365Properties()
            }
            catch
            {
                $microsoft365Properties = $NULL # No Microsoft 365 account
            }
            
            if ($microsoft365Properties -ne $NULL)
            {
                # Check assigned licenses
                $licenses = $microsoft365Properties.Licenses

                foreach ($license in $licenses)
                {
                    if ($license.Assigned)
                    {
                        $isLicensed = $True
                        break
                    }
                }
            }
            $record.IsLicensed = $isLicensed
        }
        $records += $record
    }
    
    # Export members
    $records | Export-Csv -NoTypeInformation -Path $csvFilePath
}
finally
{
    # Release resources used by search
    if ($searchResultIterator) { $searchResultIterator.Dispose() }
}

Comments 0
Leave a comment
Loading...

Got questions?

Support Questions & Answers