################################################ # Script Name: Create-AllUsersMoveRequests.ps1 # Author: Kevin Sparenberg # Purpose: Create move requests for all active users and balance the database sizes ################################################ # Clean up any variables that are still sitting out there suppressing errors Get-Variable | Remove-Variable -ErrorAction SilentlyContinue # Add the Exchange 2010 PowerShell Snapin (if not already loaded), suppressing errors Add-PSSnapin Microsoft.Exchange.Management.PowerShell.E2010 -ErrorAction SilentlyContinue $CreateMoveRequests = $true # Get all 2010 Databases $TargetDatabases = Get-MailboxDatabase -Status | Sort-Object Name # Build a New Collection to Track the Database Size as mailboxes are added $TargetDBs = @() $TargetDatabaseCount = $TargetDatabases.Count $i = 1 # Counter ForEach ( $TargetDatabase in $TargetDatabases ) { Write-Progress -Activity "Building Custom Mailbox Database Object Collection" -Status ( "Target Database [" + $i + "/" + $TargetDatabaseCount + "]" ) -CurrentOperation ( "Building Custom Object for Database: " + $TargetDatabase.Name ) -PercentComplete ( ( $i / $TargetDatabaseCount ) * 100 ) $TargetDBItem = New-Object PSObject $TargetDBItem | Add-Member -MemberType NoteProperty -Name Name -Value $TargetDatabase.Name $TargetDBItem | Add-Member -MemberType NoteProperty -Name OriginalSize -Value $TargetDatabase.DatabaseSize $TargetDBItem | Add-Member -MemberType NoteProperty -Name OriginalWhiteSpace -Value $TargetDatabase.AvailableNewMailboxSpace $TargetDBItem | Add-Member -MemberType NoteProperty -Name ProjectedSize -Value ( $TargetDatabase.DatabaseSize - $TargetDatabase.AvailableNewMailboxSpace ) $TargetDBItem | Add-Member -MemberType NoteProperty -Name MailboxCount -Value ( ( Get-Mailbox -ResultSize Unlimited -Database $TargetDatabase | Measure-Object ).Count ) $TargetDBs += $TargetDBItem $i++ } Write-Progress -Activity "Building Custom Mailbox Database Object Collection" -Status "Completed" -Completed # Get all Legacy Mailboxes and Filter off any we don't want $LegacyMailboxes = Get-ExchangeServer | Where-Object { -not $_.IsE14orLater -and $_.IsMailboxServer -and $_.Name -like "*EXMBX*" } | Get-Mailbox -ResultSize Unlimited -Filter { WindowsEmailAddress -like "*@dlapiper.com" -and CustomAttribute1 -ne $null -and CustomAttribute4 -notlike "TERM*" } # Create an empty collection for the move requests $MoveRequests = @() $LegacyMailboxCount = $LegacyMailboxes.Count $i = 1 # Counter ForEach ( $Mailbox in $LegacyMailboxes ) { Write-Progress -Activity "Building Custom Mailbox Object Collection" -Status ( "Determining Target Database for Mailbox [" + $i + "/" + $LegacyMailboxCount + "]" ) -CurrentOperation ( "Building Custom Object for Mailbox: " + $Mailbox.DisplayName ) -PercentComplete ( ( $i / $LegacyMailboxCount ) * 100 ) if ( $Mailbox.Identity -notlike "*Disabled*" ) { $MoveRequest = New-Object PSObject $MoveRequest | Add-Member -MemberType NoteProperty -Name DisplayName -Value $Mailbox.DisplayName $MoveRequest | Add-Member -MemberType NoteProperty -Name Department -Value $Mailbox.CustomAttribute14 $MoveRequest | Add-Member -MemberType NoteProperty -Name Office -Value $Mailbox.Office $MoveRequest | Add-Member -MemberType NoteProperty -Name MBXIdentity -Value $Mailbox.Identity $MoveRequest | Add-Member -MemberType NoteProperty -Name MBXSize -Value ( ( Get-MailboxStatistics $Mailbox ).TotalItemSize ) if ( $Mailbox.ServerName.SubString(0,4) -eq "SAND" ) { $MoveRequest | Add-Member -MemberType NoteProperty -Name DataCenter -Value "West" } elseif ( $Mailbox.ServerName.SubString(0,4) -eq "BALT" ) { $MoveRequest | Add-Member -MemberType NoteProperty -Name DataCenter -Value "East" } else { $MoveRequest | Add-Member -MemberType NoteProperty -Name DataCenter -Value "????" } # Add the empty Target Database Field to the Move Object $MoveRequest | Add-Member -MemberType NoteProperty -Name TargetDB -Value $null $MoveRequests += $MoveRequest $i++ } } Write-Progress -Activity "Building Custom Mailbox Object Collection" -Status "Completed" -Completed # Sort the Legacy Mailboxes by Mailbox Size (Largest First) $MoveRequests = $MoveRequests | Sort-Object MBXSize -Descending $MoveRequestCount = $MoveRequests.Count $i = 1 # Counter ForEach ( $MoveRequest in $MoveRequests ) { Write-Progress -Activity "Determining Mailbox Placement" -Status ( "Determining Target Database for Mailbox [" + $i + "/" + $MoveRequestCount + "]" ) -CurrentOperation ( "Assigning Target Database for Mailbox: " + $MoveRequest.DisplayName ) -PercentComplete ( ( $i / $MoveRequestCount ) * 100 ) $MoveRequest.TargetDB = ( $TargetDBs | Where-Object { $_.Name -like ( $MoveRequest.DataCenter + "*" ) } | Sort-Object ProjectedSize )[0].Name ( $TargetDBs | Where-Object { $_.Name -like ( $MoveRequest.DataCenter + "*" ) } | Sort-Object ProjectedSize )[0].ProjectedSize += $MoveRequest.MBXSize.Value ( $TargetDBs | Where-Object { $_.Name -like ( $MoveRequest.DataCenter + "*" ) } | Sort-Object ProjectedSize )[0].MailboxCount++ $i++ } Write-Progress -Activity "Determining Mailbox Placement" -Status "Completed" -Completed if ( $CreateMoveRequests ) { $i = 1 # Counter ForEach ( $Move in $MoveRequests ) { Write-Progress -Activity "Creating Move Requests" -Status ( "Creating Move Request [" + $i + "/" + $MoveRequestCount + "]" ) -CurrentOperation ( "Creating Move Request for " + $Move.DisplayName ) -PercentComplete ( ( $i / $MoveRequestCount ) * 100 ) ( $Move.MBXIdentity ) | New-MoveRequest -BatchName ( $Move.TargetDB ) -TargetDatabase ( $Move.TargetDB ) -SuspendWhenReadyToComplete $i++ } Write-Progress -Activity "Creating Move Requests" -Status "Completed" -Completed } else { # Output the Mailbox Move Information if we're not going to create the requests $MoveRequests } # Output the Target Database Information $TargetDBs