Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

C# VSTO Outlook plugin - How can I get the email address of the sender of an outgoing email using Exchange?

There are a few questions on this already, but I am facing a different issue. The solutions posted on other questions didn't work for me, I suspect the reason is that I am trying to get the senders email address of an outgoing email, rather than one that has been sent from someone else and is sitting in a mail folder.

What I am trying to do

Put simply, I am writing an Outlook plugin which hooks into the "ItemSend" event and runs a function to display the senders email (SMTP) address when they click "Send" on an email.

The issue

I am unable to get the SMTP address when an email is sent from an Exchange mailbox. Instead, mail.SenderEmailAddresss gives an X400 address, other methods I have found either give an exception, or don't return an email address at all.

GetSenderSMTPAddress(mail) gives blank output

mail.SenderEmailAddresss results in: /o=Company Organisation/ou=Exchange Administrative Group (ABC123T)/cn=Recipients/cn=abc123-

mail.Sender.Address resulted in Exception thrown: 'System.NullReferenceException' in OutlookTesting.dll

The code I have at the moment

namespace OutlookTesting
{
    public partial class ThisAddIn
    {
        private void ThisAddIn_Startup(object sender, System.EventArgs e)
        {
            this.Application.ItemSend += new Microsoft.Office.Interop.Outlook.ApplicationEvents_11_ItemSendEventHandler(Application_ItemSend);
        }

        void Application_ItemSend(object Item, ref bool Cancel)
        {
            if (Item is Outlook.MailItem)
            {
                Outlook.MailItem mail = (Outlook.MailItem)Item;
                Debug.WriteLine("Using GetSenderSMTPAddress function: " + GetSenderSMTPAddress(mail));
                Debug.WriteLine("Using mail.SenderEmailAddresss: " + mail.SenderEmailAddress);
                Debug.WriteLine("Using mail.Sender.Address: " + mail.Sender.Address);
            }
        }

        private string GetSenderSMTPAddress(Outlook.MailItem mail)
        {
            string PR_SMTP_ADDRESS =
                @"http://schemas.microsoft.com/mapi/proptag/0x39FE001E";
            if (mail == null)
            {
                throw new ArgumentNullException();
            }
            if (mail.SenderEmailType == "EX")
            {
                Outlook.AddressEntry sender = mail.Sender;
                if (sender != null)
                {
                    //Now we have an AddressEntry representing the Sender
                    if (sender.AddressEntryUserType ==
                        Outlook.OlAddressEntryUserType.
                        olExchangeUserAddressEntry
                        || sender.AddressEntryUserType ==
                        Outlook.OlAddressEntryUserType.
                        olExchangeRemoteUserAddressEntry)
                    {
                        //Use the ExchangeUser object PrimarySMTPAddress
                        Outlook.ExchangeUser exchUser =
                            sender.GetExchangeUser();
                        if (exchUser != null)
                        {
                            return exchUser.PrimarySmtpAddress;
                        }
                        else
                        {
                            return null;
                        }
                    }
                    else
                    {
                        return sender.PropertyAccessor.GetProperty(
                            PR_SMTP_ADDRESS) as string;
                    }
                }
                else
                {
                    return null;
                }
            }
            else
            {
                return mail.SenderEmailAddress;
            }
        }
        #region VSTO generated code

        /// <summary>
        /// Required method for Designer support - do not modify
        /// the contents of this method with the code editor.
        /// </summary>
        private void InternalStartup()
        {
            this.Startup += new System.EventHandler(ThisAddIn_Startup);
        }

        #endregion
    }
}

Other things I have tried

I tried the solution here: https://learn.microsoft.com/en-us/office/client-developer/outlook/pia/how-to-get-the-smtp-address-of-the-sender-of-a-mail-item. This didn't work, and instead gave a NullReferenceException.

I did also fall back to assuming the default mailbox was the senders email address, but this is a bad idea for those with multiple mailboxes.

Closing thoughts

I'm thinking that the only solution (other than a 3rd party plugin) would be to loop through each mailbox on the account, grab the X400 address (if exchange mailboxes) and put in an array with the email address. When an email is being sent, grab the X400 from the outgoing email, match it to the account's X400 and then I will have the email address. Not sure if this is possible or even a decent solution just yet though.

like image 429
user2924019 Avatar asked Nov 25 '20 14:11

user2924019


People also ask

What C is used for?

C programming language is a machine-independent programming language that is mainly used to create many types of applications and operating systems such as Windows, and other complicated programs such as the Oracle database, Git, Python interpreter, and games and is considered a programming foundation in the process of ...

What is C language?

C is an imperative procedural language supporting structured programming, lexical variable scope, and recursion, with a static type system. It was designed to be compiled to provide low-level access to memory and language constructs that map efficiently to machine instructions, all with minimal runtime support.

Why is C named so?

Quote from wikipedia: "A successor to the programming language B, C was originally developed at Bell Labs by Dennis Ritchie between 1972 and 1973 to construct utilities running on Unix." The creators want that everyone "see" his language. So he named it "C".

What is C full form?

In the real sense it has no meaning or full form. It was developed by Dennis Ritchie and Ken Thompson at AT&T bell Lab. First, they used to call it as B language then later they made some improvement into it and renamed it as C and its superscript as C++ which was invented by Dr.


1 Answers

I had to find a work around. I'm still using the GetSenderSMTPAddress function within the question, but noticed GetSenderSMTPAddress will work fine if it is the secondary mailbox, and will be null if it's the primary mailbox, in which case you can use mailItem.SendUsingAccount.SmtpAddress.

if (GetSenderSMTPAddress(mailItem) != null) // secondary or additional mailbox
{
    sendingAddress = GetSenderSMTPAddress(mailItem);
}
else //primary mailbox
{
    sendingAddress = mailItem.SendUsingAccount.SmtpAddress;
}
like image 73
user2924019 Avatar answered Oct 20 '22 02:10

user2924019