Overview:

This comprehensive guide provides PowerShell commands for migrating email domains in hybrid Microsoft 365 and Active Directory environments. The scripts cover updating User Principal Names (UPNs), managing Exchange Online mailbox addresses, and configuring Active Directory proxy addresses.

 

⚠️ Important Warning: These scripts make significant changes to user accounts and email addresses. Always test in a non-production environment first and ensure you have proper backups before running in production.

Prerequisites

Before running these scripts, ensure you have the following:

  • PowerShell Modules:
    • Microsoft.Graph (for Azure AD/Entra ID operations)
    • ExchangeOnlineManagement (for Exchange Online operations)
    • ActiveDirectory (for on-premises AD operations)
  • Permissions:
    • User.ReadWrite.All and Directory.ReadWrite.All in Microsoft Graph
    • Exchange Administrator role for Exchange Online
    • Domain Administrator or delegated permissions for Active Directory
  • Network Access: Connectivity to Microsoft 365 and your on-premises Active Directory

Step 1: Update User Principal Names (Microsoft Graph)

1

Purpose: Update user UPNs from the old domain (@contoso.com) to the new domain (@fabrikam.net)

Script Explanation

This script connects to Microsoft Graph and updates user principal names for all users in the specified domain. It also cleans up proxy addresses to remove references to the old domain.

# Connect to Microsoft Graph with required permissions
Connect-MgGraph -Scopes "User.ReadWrite.All","Directory.ReadWrite.All"

# Update UPNs
$filteredUsers = Get-MgUser -All
$users = $filteredUsers | Where-Object { $_.UserPrincipalName -like "*@contoso.com" }

foreach ($user in $users) {
    $oldUpn = $user.UserPrincipalName
    $newUpn = $oldUpn -replace "@contoso.com","@fabrikam.net"
    Update-MgUser -UserId $user.Id -UserPrincipalName $newUpn -MailNickname ($newUpn.Split("@")[0])
    $updatedAddresses = $user.ProxyAddresses | Where-Object { $_ -notmatch $oldUpn }
    Update-MgUser -UserId $user.Id -ProxyAddresses $updatedAddresses
    Write-Host "Updated UPN for user: $($user.DisplayName) from $oldUpn to $newUpn"
    Write-Host "Updated ProxyAddresses for user: $($user.DisplayName) to $updatedAddresses"
}

What This Script Does:

  • Connects to Microsoft Graph with necessary permissions
  • Retrieves all users with UPNs ending in @contoso.com
  • Updates each user’s UPN to use @fabrikam.net
  • Updates the mail nickname to match the new UPN
  • Removes old proxy addresses containing the old domain
  • Provides console output for tracking progress

Step 2: Clean Up Exchange Online Mailbox Addresses

2

Purpose: Remove old email addresses from Exchange Online mailboxes

Script Explanation

This script connects to Exchange Online and removes all email addresses containing the old domain from user mailboxes.

# Connect to Exchange Online
Connect-ExchangeOnline

# Get all mailboxes
$mailboxes = Get-Mailbox -ResultSize Unlimited

foreach ($mailbox in $mailboxes) {
    $originalAddresses = $mailbox.EmailAddresses
    $filteredAddresses = @()
    
    $hasRemoved = $false
    
    foreach ($address in $originalAddresses) {
        if ($address -like "*@contoso.com") {
            Write-Host "Removing address: $address from $($mailbox.PrimarySmtpAddress)"
            $hasRemoved = $true
        } else {
            $filteredAddresses += $address
        }
    }
    
    if ($hasRemoved) {
        Set-Mailbox -Identity $mailbox.Identity -EmailAddresses $filteredAddresses
    }
}

What This Script Does:

  • Connects to Exchange Online PowerShell
  • Retrieves all mailboxes in the organization
  • Examines each mailbox’s email addresses
  • Removes any addresses containing @contoso.com
  • Updates the mailbox with the filtered address list
  • Only updates mailboxes where addresses were actually removed

Step 3: Add Proxy Addresses in Active Directory

3

Purpose: Add new proxy addresses to users in Active Directory

Script Explanation

This script adds new proxy addresses to users in a specified Active Directory Organizational Unit (OU).

# Define the OU and the proxy address domain
$OU = "OU=Users,DC=example,DC=com" # Replace with your target OU
$ProxyDomain = "newdomain.com" # Replace with your desired proxy domain

# Import Active Directory module
Import-Module ActiveDirectory

# Get all users in the specified OU
$Users = Get-ADUser -Filter * -SearchBase $OU -Properties proxyAddresses, mail

foreach ($User in $Users) {
    # Construct the new proxy address
    $PrimaryEmail = $User.mail
    if ($PrimaryEmail) {
        $Username = $PrimaryEmail.Split("@")[0]
        $NewProxy = "smtp:$Username@$ProxyDomain"
        
        # Check if the proxy address already exists
        if (-not ($User.proxyAddresses -contains $NewProxy)) {
            # Add the new proxy address
            Set-ADUser -Identity $User.DistinguishedName -Add @{proxyAddresses=$NewProxy}
            Write-Host "Added proxy address $NewProxy to $($User.SamAccountName)"
        } else {
            Write-Host "Proxy address $NewProxy already exists for $($User.SamAccountName)"
        }
    } else {
        Write-Host "User $($User.SamAccountName) does not have a primary email address."
    }
}

Configuration Required:

  • $OU: Replace with your target Organizational Unit distinguished name
  • $ProxyDomain: Replace with your new domain name

What This Script Does:

  • Imports the Active Directory PowerShell module
  • Retrieves users from the specified OU with email properties
  • Constructs new proxy addresses using the new domain
  • Checks for existing proxy addresses to avoid duplicates
  • Adds new proxy addresses to user accounts
  • Provides detailed logging of all operations

Best Practices and Considerations

Testing and Validation:

  • Always test scripts in a development environment first
  • Run scripts on a small subset of users initially
  • Verify changes before proceeding with the full migration

Execution Order

Execute the scripts in the following order for optimal results:

  1. Step 1: Update UPNs in Microsoft Graph
  2. Step 2: Clean up Exchange Online addresses
  3. Step 3: Add proxy addresses in Active Directory

Monitoring and Logging

  • Monitor the console output during script execution
  • Consider adding additional logging to files for audit purposes
  • Verify changes in both the Microsoft 365 admin center and Active Directory

Rollback Considerations

  • Document original UPNs and email addresses before making changes
  • Consider creating backup scripts to reverse changes if needed
  • Test rollback procedures in your development environment

Common Issues and Troubleshooting

  • Permission Errors: Ensure you have the required administrative permissions
  • Module Not Found: Install required PowerShell modules before running scripts
  • Connection Timeouts: Consider adding retry logic for large environments
  • Duplicate Addresses: The scripts include checks to prevent duplicate proxy addresses