Azure AD Users WriteBack to Active Directory On-Prem using PowerShell

In this article, I am going to share with you how to write back user accounts from Azure AD to Active Directory On-Prem using with PowerShell.

Scenario
You have some user accounts in your Azure AD tenant that are not synchronized to your AD on-prem, you want to create them in your on-prem Active Directory with the same properties so that they could merge and become hybrid identities, this way they could access your local network resources.

Contraints
– You don’t want to make change to your existing infrastructure,
– You have an Azure AD that synchronizes identies from your on-prem Active Directory to your Azure AD tenant but you want no change to its configurations.

Solution
Use a powershell script to create those accounts in AD on-prem and let AAD Connect synchronize those new created accounts to Azure AD and merge them. After this operation, user accounts are transformed to hybrid identies.

What should the script do
Read account properties in Azure AD and create them in Active Directoy on-prem.

Warning
With this solution, be aware that new password will be set for each users as they are going to be created in on-prem Active Directory.

Prerequisites for using the script
You should have PowerShell module installed
All upn suffixes (generally all verified domains) of your tenant must be added as upn suffixes in your on-prem Active Directory so they could be used to create upns.

Prepare your input files
It contains userprincipalname of Azure AD User accounts you want to create on your Active Directory on-prem.

Everything is set now, let’s run the script.

Run the script
Change the variables of the script to adapt them to your environment.

#Connect to Azure AD
Connect-AzureAD

#Variables
$UsersToWB = Import-Csv -path "C:\Temp\AADUsers.csv" -Encoding UTF8 #file containing userprincipalname of Azure AD Users you want to writeback to AD on-prem
$ProxyAddresseUpdated = "C:\Temp\ProxyAddressesUpdated.csv" #Log file
$Path = "OU Distinguished name" #Example : $Path = "OU=Sales,OU=UserAccounts,DC=CONTOSO,DC=COM" #Distinghishedname of the organizational unit where user account are going to be created.
$ExistInADOnPrem = "C:\Temp\ExistInADOnPrem.csv"

$Server = (Get-ADDomainController -Discover -Service ADWS).Name #Find a domain controller 
$ADUsers = Get-ADUser -Filter * -Properties * -Server $Server   #Load all AD on-prem User accounts
$AADUsers = Get-AzureADUser -All $true -filter "UserType eq 'Member'" #Load all Azure AD User accounts of type Member

#Creating account in AD on-prem
foreach ($UserToWB in $UsersToWB){

    #Check that user account doesn't exist in your AD on-prem domain before creating them
    $adopUser = $ADUsers | where-object {($_.UserPrincipalName -eq $UserToWB.UserPrincipalName) -or ($UserToWB.UserPrincipalName -in $_.ProxyAddresses)}
    if(($adopUser | Measure-Object).count -ge 1){
        $adopUser | Select-Object UserPrincipalName, DistinguishedName | Export-Csv -Path $ExistInADOnPrem -Encoding UTF8 -Delimiter ";" -NoTypeInformation -Append
    }
    else{
        #Create user account. At this step, we are sure user account does not exist in AD on-prem
        Write-Host "Start Creation $($UserToWB.UserPrincipalName)" -ForegroundColor Yellow

        #Get Azure AD User data
        $AADUser = $AADUsers | Where-Object {$_.UserPrincipalName -eq $UserToWB.UserPrincipalName}        

        #Building samAccountName
        $samAccountName = ($AADUser.UserPrincipalName -split("@"))[0]
        if($samAccountName.Length -gt 20){
            $samAccountName = $samAccountName[0..19] -join ""
        }

        $DefaultPWD = ConvertTo-SecureString -AsPlainText $UserToWB.Password -force

        #Creating AD User account 
        New-ADUser $samAccountName -GivenName $AADUser.GivenName -Surname $AADUser.Surname `
            -Company $AADUser.CompanyName -Department $AADUser.department -EmployeeID $AADUser.ExtensionProperty.employeeId `
                -PostalCode $AADUser.postalCode -UserPrincipalName $AADUser.UserPrincipalName `
                    -EmailAddress $AADUser.mail -title $AADUser.JobTitle `
                        -StreetAddress $AADUser.StreetAddress -City $AADUser.City `
                            -Enabled $AADUser.AccountEnabled -ChangePasswordAtLogon $false `
                                -Office $AADUser.PhysicalDeliveryOfficeName -Path $Path `
                                    -AccountPassword $DefaultPWD -Server $Server
    
        #Set DisplayName and ProxyAddresses
        do{
            Start-Sleep -Seconds 1
            $NewUser = Get-ADUser -filter "UserPrincipalname -eq '$($AADUser.UserPrincipalName)'" -Properties * -Server $Server
        } while(-not $NewUser)

        #Set DisplayName
        Set-ADUser $NewUser.DistinguishedName -DisplayName $AADUser.DisplayName -Server $Server
        Rename-ADObject -Identity $NewUser.DistinguishedName -NewName $AADUser.DisplayName -Server $Server

        #Set ProxyAddresses 
        $Addresses = $AADUser | Select-Object -ExpandProperty ProxyAddresses | Where-Object {$_ -notlike "onmicrosoft.com"} 
        Start-Sleep -Seconds 2
        if($Addresses){
            ForEach($Address in $Addresses){
                Write-Host "Adding Proxy Address: $Address" -ForegroundColor White
                Set-ADUser -Identity $NewUser.ObjectGUID.Guid -Add @{ProxyAddresses="$Address"} -Server $Server
                if($?) {
                    Write-Host "Proxy OK: $Address" -ForegroundColor Green
                    $NewUser | Select-Object UserPrincipalName, @{Name ="Address"; Expression ={$Address}}, @{Name = "Added"; Expression = {$true}} | Export-Csv -Path $ProxyAddresseUpdated -Delimiter ";" -Encoding UTF8 -NotypeInformation -Append
                }
                else {
                    Write-Host "Proxy NOK: $Address" -ForegroundColor Red
                    $NewUser | Select-Object UserPrincipalName, @{Name ="Address"; Expression ={$Address}}, @{Name = "Added"; Expression = {$false}} | Export-Csv -Path $ProxyAddresseUpdated -Delimiter ";" -Encoding UTF8 -NotypeInformation -Append
                }
            }
        }
        Write-Host "Done: $($UserToWB.UserPrincipalName)" -ForegroundColor Green
    }
}

Script outpout in Powershell Console

Log file produced by the script will look like below content

Check script result in your Active Directoy

Thank you.

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 )

Connecting to %s