Welcome to Powergui.org - an open source community for Windows Powershell

PowerGUI.org PowerGUI.org and blogs

Forums » PowerGUI User Discussions

Thread: multithreaded mailbox move question

This question is answered.


Permlink Replies: 5 - Pages: 1 - Last Post: Dec 7, 2009 9:36 AM by: mtupker_187
mtupker_187

Posts: 3
Registered: 12/3/09
multithreaded mailbox move question
Posted: Dec 3, 2009 5:18 PM
 
  Click to reply to this thread Reply

I've writen a script to move mailboxes from an exchange 2003 server to a 2007 server. The script is working however I can't seem to get it to do more than one mailbox at a time. If any one has some suggestions on how it could be modified to run multithreaded I'd love some input. Essentially the script will only move mailboxes of users that are a member of a specific security group. Here is the script.

$colResults = Get-QADUser -SearchRoot mtmercy.edu/IT/testing

foreach ($i in $colResults)
    {
        #Check if user is in staff group
        if ((Get-QADUser -identity $i).memberof -eq "CN=Sonicwall - Staff,OU=Sonicwall,OU=Security Groups,DC=mtmercy,DC=edu")
        {
            Write-Host "found staff"
            Write-Host "Moving" $i
           
            Move-Mailbox -Identity $i.samAccountName -TargetDatabase "exchangehub\First Storage Group\Mailbox Database" -SourceMailboxCleanupOptions DeleteSourceMailbox -confirm:$false
            add-QADGroupMember -identity "CN=Sonicwall - Exchangehub,OU=Sonicwall,OU=Security Groups,DC=mtmercy,DC=edu" -member $i.dn
            Remove-QADGroupMember -Identity "CN=Sonicwall - Staff,OU=Sonicwall,OU=Security Groups,DC=mtmercy,DC=edu" -Member $i.dn
            Remove-QADGroupMember -Identity "CN=Sonicwall - Faculty,OU=Sonicwall,OU=Security Groups,DC=mtmercy,DC=edu" -Member $i.dn
        }

UPDATE:
I also noticed that when run it uses a LOT of RAM. I'm open to any suggestions on how to improve it overall.
Message was edited by: mtupker_187


antize


Posts: 122
Registered: 2/21/09
Re: multithreaded mailbox move question
Posted: Dec 3, 2009 7:14 PM   in response to: mtupker_187
 
  Click to reply to this thread Reply

If your using PS V2 you can spin up a hand full of moves to run at once with background jobs. It would probably be a good idea to throttle the amount of background jobs you've got going on at once.

You'll need a script block  or a script file to execute as a background task. Here is an example of a script block that downloads a file:

$GetWebFile = {
    param
    (
        [System.Uri]$Address,
        [System.IO.FileInfo]$File
    )
    if ($File.Exists)
    {
        $File.Delete()
    }
    $client = New-Object System.Net.WebClient
    $client.Proxy = [System.Net.WebRequest]::DefaultWebProxy
    $client.Proxy.Credentials = [System.Net.CredentialCache]::DefaultNetworkCredentials
    $client.DownloadFile($Address.AbsoluteUri, $File.Fullname)
}

Here is a big script that downloads ten large files 2 at a time:

$urls = @(
    'http://ecn.channel9.msdn.com/o9/ch9/3/1/5/0/1/5/BugCamSmash_ch9.mp4',                                          
    'http://ecn.channel9.msdn.com/o9/ch9/7/5/2/5/0/5/VEV_ch9.mp4',                                                      
    'http://ecn.channel9.msdn.com/o9/ch9/3/1/2/4/0/5/C9LecturesMeijerFPC10_ch9.mp4',                                
    'http://ecn.channel9.msdn.com/o9/ch9/1/6/2/5/0/5/BTCNickBaker_ch9.mp4',                                             
    'http://ecn.channel9.msdn.com/o9/ch9/0/5/0/3/0/5/StreetSide_ch9.mp4',                                               
    'http://ecn.channel9.msdn.com/o9/ch9/4/4/0/8/0/5/coding4funAtPdc_ch9.mp4',                                          
    'http://ecn.channel9.msdn.com/o9/ch9/5/4/2/8/0/5/AcessManagingDatabases_ch9.mp4',                                   
    'http://ecn.channel9.msdn.com/o9/ch9/8/4/1/0/1/5/PDCGeekFest_ch9.mp4',                                              
    'http://ecn.channel9.msdn.com/o9/ch9/4/4/8/9/8/4/JeffHadfieldVSDocumentary_ch9.mp4',                                
    'http://ecn.channel9.msdn.com/o9/ch9/0/6/8/8/0/5/SUYTMP2_ch9.mp4'
)                                                

$GetWebFile = {
    param
    (
        [System.Uri]$Address,
        [System.IO.FileInfo]$File
    )
    if ($File.Exists)
    {
        $File.Delete()
    }
    $client = New-Object System.Net.WebClient
    $client.Proxy = [System.Net.WebRequest]::DefaultWebProxy
    $client.Proxy.Credentials = [System.Net.CredentialCache]::DefaultNetworkCredentials
    $client.DownloadFile($Address.AbsoluteUri, $File.Fullname)
}

$CueLimit = 2
$downloadFolder = [System.IO.DirectoryInfo] "D:\Video"
Write-Host ("Downloading files to: " + $downloadFolder.FullName) -ForegroundColor Cyan

$urls | % {
    [Uri] $url = $_
    $fileName = $url.Segments[-1]
    [System.IO.FileInfo] $downloadFile = Join-Path $downloadFolder.FullName $fileName
   
    # Start a background job for file download
    $job = Start-Job -Name $downloadFile.Name -ScriptBlock $GetWebFile -ArgumentList $url.AbsoluteUri, $downloadFile.FullName
   
    # Get currently running job ID list
    [int[]]$ids = Get-Job | ? {($_.Command -eq $job.command) -and ($_.State -eq "Running")} | % {$_.id}
   
    # If the cue limit is maxed, wait for a download to finish before starting a new one
    if ( ($ids -ne $null) -and ( ($ids.Count % $CueLimit) -eq 0) )
    {
        Wait-Job -Id $ids -Any | % {Write-Host ("Completed: " + $_.Name)}
    }
}




Shay Levy


Posts: 1,919
Registered: 1/31/08
Re: multithreaded mailbox move question
Posted: Dec 6, 2009 1:30 AM   in response to: mtupker_187
 
  Click to reply to this thread Reply

You have to pipe all mailbox objects to move-mailbox, try this way:

Get-QADGroupMember 'Sonicwall - Staff' | foreach {
             Write-Host "found staff"
             Write-Host "Moving $_"

             $null = Add-QADGroupMember -identity "CN=Sonicwall - Exchangehub,OU=Sonicwall,OU=Security Groups,DC=mtmercy,DC=edu" -member $_.dn
             $null = Remove-QADGroupMember -Identity "CN=Sonicwall - Staff,OU=Sonicwall,OU=Security Groups,DC=mtmercy,DC=edu" -Member $_.dn
             $null = Remove-QADGroupMember -Identity "CN=Sonicwall - Faculty,OU=Sonicwall,OU=Security Groups,DC=mtmercy,DC=edu" -Member $_.dn
             Get-Mailbox $_.samAccountName
 
} | Move-Mailbox -TargetDatabase "exchangehub\First Storage Group\Mailbox Database" -SourceMailboxCleanupOptions DeleteSourceMailbox -confirm:$false


Message was edited by: Shay Levy

Shay Levy [MVP]
http://blogs.microsoft.co.il/blogs/ScriptFanatic
PowerShell Toolbar
mtupker_187

Posts: 3
Registered: 12/3/09
Re: multithreaded mailbox move question
Posted: Dec 7, 2009 7:53 AM   in response to: Shay Levy
 
  Click to reply to this thread Reply

Ah, I figured it was something with the program flow but wasn't sure. (Still a powershell beginner). I have a couple questions though if you don't mind.

Is there a way to limit it to just one OU (and sub OUs)?

Also, I ran a test without the add/remove-qadgroupmember and move-mailbox commands and hit a few users that have had their account names changed. So getting the mailbox with the samAccountName is running into some errors. Not the end of the world but is there another attribute that I can pass to the move-mailbox command other than samAccountName? I've noticed that the move-mailbox command if pretty picky about what it will take in terms of identity.

Why bother to set the qadGroupmember commands to $Null? I assume there is a functional reason, but like I said I'm new at this.

Sorry for all the questions. Just trying to get a handle on it. :)



Shay Levy


Posts: 1,919
Registered: 1/31/08
Re: multithreaded mailbox move question
Posted: Dec 7, 2009 8:33 AM   in response to: mtupker_187
Answered
  Click to reply to this thread Reply

1. To limit to just one OU (and sub OU's):

Get-QADGroupMember 'Sonicwall - Staff' -Type user | Where-Object {$_.ParentContainerDN -like '*OUDistinguishedName'}

Notice that I've also used ' -Type user' to limit the result to just user accounts (in case there are other object type members).


2. You can use any of the following as the mailbox identity:

    * GUID
    * Distinguished name (DN)
    * Domain\Account
    * User principal name (UPN)
    * LegacyExchangeDN
    * SmtpAddress
    * Alias
   

3. Add/Remove-QADGroupMember emits the objects it proceessed and if you won't suppress the output they'll become the input for Move-Mailbox.




Shay Levy [MVP]
http://blogs.microsoft.co.il/blogs/ScriptFanatic
PowerShell Toolbar
mtupker_187

Posts: 3
Registered: 12/3/09
Re: multithreaded mailbox move question
Posted: Dec 7, 2009 9:36 AM   in response to: Shay Levy
 
  Click to reply to this thread Reply

Thanks, that helps a ton!



Legend
MVP: 2501 + pts
Guru: 2001 - 2500 pts
Expert: 751 - 2000 pts
Enthusiast: 31 - 750 pts
Novice: 0 - 30 pts
Moderators
Helpful answer (5 pts)
Answered (10 pts)

Point your RSS reader here for a feed of the latest messages in all forums