none
create multiple mapi sessions simultaneously RRS feed

  • Question

  • Hi,

    Environment: C# , exchange 2010 , outlook 2007.

    I have developed a utility which accesses a specific folder and deletes all messages that comply with a certain restriction (I have more than 2 milion messages in that folder). The process is done using interop for outlook 2007.

    The program worked very slow (about 100 deletions per minute), So, I have converted the program as follows:

    I have created a backgroundWorker (Async) which collects 10 messages ID's and sends the messages ID's to another backgroundworker to make the deletion. I have 20 different worker threads for the deletion process and I am spreading the work among them. BUT, although I am working with 20 threads the deletion is not faster. I guess it has to do something with the mapi session. I am using the same mapi session in all threads. I would like to know if it is posibble to create 20 mapi sessions (1 for each thread) ? I mean that they will all work simultaneously.

    I am attaching my code.

    namespace DeleteOutlookMessagesByFilter
    
    {
    
        public partial class Form1 : Form
    
        {
    
            Microsoft.Office.Interop.Outlook.Application objOutlookApp;
    
            NameSpace objOutlookNS;
    
            MAPIFolder SourceFolder;
    
            MAPIFolder BaseFolder;
    
    
            private const int MaxThreads = 20;
    
            private BackgroundWorker[] threadArray = new BackgroundWorker[MaxThreads];
    
            private string[] ListOfMessageIDS = new string[MaxThreads];
    
    
            private void InitializeBackgoundWorkers()
    
            {
    
                for (var f = 0; f < MaxThreads; f++)
    
                {
    
                    threadArray[f] = new BackgroundWorker();
    
                    threadArray[f].DoWork += new DoWorkEventHandler(BackgroundWorkerMessageDoWork);
    
                    threadArray[f].RunWorkerCompleted += new RunWorkerCompletedEventHandler(BackgroundWorkerMessageRunWorkerCompleted);
    
                    threadArray[f].ProgressChanged += new ProgressChangedEventHandler(BackgroundWorkerMessageRunWorkerReportProgress);
    
                    threadArray[f].WorkerReportsProgress = true;
    
                    threadArray[f].WorkerSupportsCancellation = true;
    
                }
    
            }
    
    
            private void DeleteMessage(BackgroundWorker BW, string itemIDS)
    
            {
    
                try
    
                {
    
                    string[] _ItemIDS = itemIDS.Split(';');
    
                    foreach (string itemID in _ItemIDS)
    
                    {
    
                        object item = SourceFolder.Session.GetItemFromID(itemID, SourceFolder.StoreID);
    
                        if (item is MailItem)
    
                        {
    
                            ((MailItem)item).Delete();
    
                            BW.ReportProgress(_itemsCount);
    
                        }
    
                    }
    
                }
    
                catch (System.Exception)
    
                {}
    
            }
    
    
            private void BackgroundWorkerMessageDoWork(object sender, DoWorkEventArgs e)
    
            {
    
                BackgroundWorker bw = sender as BackgroundWorker;
    
    
                DeleteMessage(bw, (string)e.Argument);
    
            }
    
    
            private void BackgroundWorkerMessageRunWorkerReportProgress(object sender, ProgressChangedEventArgs e)
    
            {}
    
    
            private void BackgroundWorkerMessageRunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
    
            {}
    
    
            private MAPIFolder GetFolder(MAPIFolder BaseFolder, string FolderName)
    
            {
    
                try
    
                {
    
                    if (FolderName.Contains("\\"))
    
                    {
    
                        string CurrentFolder = FolderName.Substring(0,FolderName.IndexOf("\\"));
    
                        string NextFolderPath = FolderName.Substring(FolderName.IndexOf("\\") + 1);
    
                        return GetFolder(BaseFolder.Folders[CurrentFolder], NextFolderPath);
    
                    }
    
                    else
    
                    {
    
                        return BaseFolder.Folders[FolderName];
    
                    }
    
                }
    
                catch (System.Exception ex)
    
                {
    
                    Console.WriteLine(ex.Message);
    
                    throw;
    
                }
    
            }
    
    
            private MAPIFolder GetMailBox(NameSpace objOutlookNS , string MailboxName)
    
            {
    
                Stores MapiStores;
    
                try
    
                {
    
                    MapiStores = objOutlookNS.Stores;
    
                    foreach (Store MapiStore in MapiStores)
    
                    {
    
                        if (MapiStore.DisplayName.ToUpper() ==  MailboxName.ToUpper())
    
                        {
    
                            return MapiStore.GetRootFolder();
    
                        }
    
                    }
    
                    return null;
    
                }
    
                catch (System.Exception ex )
    
                {
    
                    MessageBox.Show(ex.Message + ex.StackTrace.ToString());
    
                    throw;
    
                }
    
            }
    
    
            private object TimeConsumingOperation(BackgroundWorker bw, int sleepPeriod)
    
            {
    
                try
    
                {
    
                    Items _items1 = SourceFolder.Items.Restrict("[MessageClass] = '" + txtMessageClass.Text + "'");
    
                    Items _items = _items1.Restrict("[ReceivedTime] <= " + "\"" + txtDate + "\"");
    
                    _items.Sort("[ReceivedTime]", true);
    
                    string TextToSearch = txtSubject.Text.ToUpper();
    
                    int Counter = 0;
    
                    string MessageIDS = "";
    
                    foreach (object item in _items)
    
                    {
    
                        if (item is MailItem)
    
                        {
    
                            MailItem _MailItem = (MailItem)item;
    
    
                            if (_MailItem != null)
    
                            {
    
                                if (_MailItem.Subject != "")
    
                                {
    
                                    try
    
                                    {
    
                                        if (_MailItem.Subject.ToUpper().Contains(TextToSearch))
    
                                        {
    
                                            Boolean AllThreadsArbBusy = true;
    
                                            Counter++;
    
                                            if (Counter % 10 == 0)
    
                                            {
    
                                                MessageIDS += _MailItem.EntryID;
    
                                                again:
    
                                                for (var threadNum = 0; threadNum < MaxThreads; threadNum++)
    
                                                {
    
                                                    if (!threadArray[threadNum].IsBusy)
    
                                                    {
    
                                                        threadArray[threadNum].RunWorkerAsync(MessageIDS);
    
                                                        MessageIDS = "";
    
                                                        AllThreadsArbBusy = false;
    
                                                        break;
    
                                                    }
    
                                                }
    
                                                if (AllThreadsArbBusy)
    
                                                {
    
                                                    Thread.Sleep(10);
    
                                                    goto again;
    
                                                }
    
                                            }
    
                                            else
    
                                            {
    
                                                MessageIDS += _MailItem.EntryID + ";";
    
                                            }
    
                                        }
    
                                    }
    
                                    catch (System.Exception){}
    
                                }
    
                                backgroundWorker1.ReportProgress(1);
    
                                Thread.Sleep(sleepPeriod);
    
                                if (backgroundWorker1.CancellationPending)
    
                                {
    
                                    break;
    
                                }
    
                            }
    
                            if (MessagesProccessed % 100 == 0)
    
                            {
    
                                GC.Collect();
    
                                GC.WaitForPendingFinalizers();
    
                            }
    
                        }
    
                    }
    
                    return "success";
    
    
                }
    
                catch (System.Exception ex )
    
                {
    
                    MessageBox.Show(ex.Message + ex.StackTrace);
    
                    return "error";
    
                }
    
    
            }
    
    
            private void button1_Click(object sender, EventArgs e)
    
            {
    
                try
    
                {
    
                    btnStart.Enabled = false;
    
                    this.Refresh();
    
    
                    objOutlookApp = new Microsoft.Office.Interop.Outlook.Application();
    
                    objOutlookNS = objOutlookApp.GetNamespace("MAPI");
    
                    BaseFolder = GetMailBox(objOutlookNS, txtMailbox.Text);
    
                    if (BaseFolder != null)
    
                    {
    
                        SourceFolder = GetFolder(BaseFolder, txtFolder.Text);
    
                        if (SourceFolder != null)
    
                        {
    
                            this.backgroundWorker1.RunWorkerAsync(1);
    
                        }
    
                        else
    
                        {
    
                            MessageBox.Show("Could not find folder");
    
                        }
    
                    }
    
                    else
    
                    {
    
                        MessageBox.Show("Could not find mailbox");
    
                    }
    
                }
    
                catch (System.Exception ex)
    
                {
    
                    MessageBox.Show(ex.Message + ex.StackTrace.ToString());
    
                }
    
            }
    
    
            private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
    
            {
    
                BackgroundWorker bw = sender as BackgroundWorker;
    
    
                int arg = (int)e.Argument;
    
    
                e.Result = TimeConsumingOperation(bw, arg);
    
    
                if (bw.CancellationPending)
    
                {
    
                    e.Cancel = true;
    
                }
    
            }
    

    Thanks in advance,

    Dov

    Wednesday, December 17, 2014 4:36 PM

Answers

All replies