Search code examples
multithreadingeventssta

Why is this COM interop event not raised whilst running under an STA thread?


Can somebody please explain why the event "OnNewMail" is not raised when using an STA thread in the code below? The program attempts to use the Redemption library to intercept incoming outlook mails.

class Program
{        
    [STAThread()] // When this line is deleted the application works
    static void Main(string[] args)
    {
        RDOSession session = GetSession();
        session.OnNewMail += Session_OnNewMail;
        Console.ReadLine();
    }

    static void Session_OnNewMail(string EntryID)
    {
         Console.WriteLine("New mail received");
    }

    private static RDOSession GetSession()
    {
        var session = new RDOSession();
        var application = new ApplicationClass();

        session.MAPIOBJECT = application.Session.MAPIOBJECT;
        return session;
    }
}

Solution

  • COM running on an STAThread uses a message pump to raise events and call methods. When in a console application there isn't a window to pump messages for you so you need to run the pump yourself. (Several of the .NET synchronisation methods will do this for you - have a look at WaitOne etc...)

    If the object is happy within a default MTA thread - you may be better off using that if you need to do this from a console application.

    Instead of ReadLine - you can poll for a key and pump messages using this:

    while (Console.Read() == 0)
    {
        Thread.CurrentThread.Join(100);
    }
    

    ...but this is a hack.

    Mixing COM, console apps and [STAThread] is a bit fishy and can result in other problems: http://support.microsoft.com/default.aspx/kb/828988