2009-08-17 15 views
11

Escribo VSTO Outlook addin en C#, y necesito distinguir si MailItem es entrante o saliente (o ninguno, cuando es, por ejemplo, un borrador).Outlook MailItem: ¿Cómo distinguir si el correo es entrante o saliente?

¿Hay alguna forma infalible de hacerlo? La mejor solución que tengo ahora sería obtener una lista de destinatarios, cc y bcc's, cargar direcciones de correo electrónico de cuentas activas y verificar si esas dos listas se cruzan, pero esto me parece bastante frágil, y espero que haya una solución mejor .

Caso de uso: me gustaría obtener una fecha relevante para un correo electrónico, que podría ser ReceivedTime, o SentOn, pero para saber cuál debo usar, debo saber si se envió o recibió un correo.

Gracias por las ideas :)

+0

¿Tiene que comprobar todos los destinatarios, cc, etc, o puede simplemente mirar el remitente? Si el propietario de la cuenta no lo envió, entonces es entrante. –

+0

¿No se han enviado todos los correos recibidos? – Roland

Respuesta

0

Tome un vistazo a la propiedad .parent del MailItem - examinar las propiedades de la carpeta para determinar si se trata de la bandeja de entrada, salida, borradores, elementos, etc. enviado

+0

Pero, ¿qué ocurre si el usuario (o las reglas de filtro de correo) ya han movido el correo a una carpeta genérica (por ejemplo, la carpeta del proyecto XYZ) con los correos entrantes y salientes? En ese caso, la entrada/salida sería una propiedad específica del correo electrónico, no de la carpeta. Buena idea, esto no se me ocurrió :). –

+0

Esa es una muy buena pregunta. No tengo una respuesta de Dios para eso. –

-3

Did ¿intenta con la propiedad MailItem.Sent?

Es cierto para entrante y falso para saliente.

+0

Nope - vea la respuesta de David http://stackoverflow.com/questions/1285713/outlook-mailitem-how-to-distinguish-whether-mail-is-incoming-or-outgoing/2370543#2370543 –

2

Vine aquí con el mismo problema. Ya que explícitamente sugiero que el usuario mueva el correo a alguna carpeta en mi uso, comprobar que Parent no ayudaría ...

Con respecto a MailItem.Sent: ¿está seguro de que MailItem.Sent funciona de esta manera? Acabo de escribir un código simple para ejecutar a través de mi bandeja de entrada y SentItems y para casi todos ellos, Sent es verdadero. Supongo que esto es realmente solo una indicación de si el correo ha sido enviado (= no es borrador) ...

1

MailItem.sent es cierto para los entrantes también.

¿Qué le parece comprobar MailItem.ReceivedByEntryID. Pero estoy seguro de que esto fallará (ReceivedByEntryID será nulo para los correos en la bandeja de entrada) si dices importar desde Outlook Express o tal vez algún otro programa de correo electrónico

Iterar a través de cuentas de correo/senderemail puede ayudar como dijiste, pero no es tonto prueba (como si cambia el nombre de la dirección de correo electrónico)

+0

¡Gracias! Esto podría funcionar para la mayoría de los usuarios, ya que no creo que muchos usuarios empresariales tengan sus correos electrónicos importados de Outlook Expres (y aunque lo hicieran, la mayoría de las operaciones útiles solo incluirían correos recientes que serían recibidos por Outlook) –

0

Puede comprobar si está dentro de Outlook.OlDefaultFolders.olFolderInbox o olFolderOutbox, entonces debe haber otros métodos que puede utilizar para comprobar si está dentro de cualquiera de estas carpetas.

Outlook.Application _application = new Outlook.Application(); 
Outlook.MAPIFolder folder = _application.GetNamespace("MAPI").GetDefaultFolder(Outlook.OlDefaultFolders.olFolderInbox); 
+0

Creo que esto no funcionaría en los correos enviados/recibidos que se han movido a otra carpeta (por ejemplo, con un filtro), ¿o sí? –

1

Resolví este problema agregando una nueva propiedad de usuario después de enviar un correo electrónico. Entonces, cuando necesito verificar si se envió un correo electrónico, verifico esta propiedad. Esto funciona incluso si el correo electrónico se movió de la carpeta Enviados. Por supuesto, esto funciona solo para los correos electrónicos recién creados, pero puede agregar esta propiedad a todos los correos electrónicos en la carpeta Enviados durante el primer inicio. El único error es que UserProperties se imprimen de manera predeterminada, pero puede ser overridden.

+1

Esta es una solución bastante pesada, pero probablemente solo una que funcione. Sin embargo, el complemento debería ejecutarse todo el tiempo, de lo contrario obtendríamos correos electrónicos recibidos sin marcar, y al primer inicio. no podríamos marcar los correos electrónicos enviados que se han movido a otra carpeta. Tal vez sería posible escanear todo el correo y ver si el destinatario es una de las direcciones de correo electrónico del usuario, pero esto podría llevar horas en una gran cuenta de intercambio/IMAP ... –

1

Así compruebo el tipo de correo y funciona incluso si el correo se mueve a cualquier carpeta. Esta solución utiliza propiedad de acceso que está disponible en Outlook 2007. A continuación se muestra el código

string PR_MAIL_HEADER_TAG = "http://schemas.microsoft.com/mapi/proptag/0x007D001E"; 

Outlook.PropertyAccessor oPropAccessor = mItemProp.PropertyAccessor; 

string strHeader = (string)oPropAccessor.GetProperty(PR_MAIL_HEADER_TAG); 

if (strHeader == "") 
{ 
    // MAIL IS OF TYPE SENTBOX 
} 
else 
{ 
    // MAIL IS OF TYPE INBOX 
} 
+1

no funciona en 2010 2010 al menos – Kumar

+0

funciona con intercambiar cuentas de correo pero no con imap/smtp - probado con ol 2016 – Lakedaimon

17

llegado a esta página porque estaba teniendo mismo problema en VBA. Comprobar las carpetas principales es engorroso, ya que un mensaje puede contener varias carpetas de profundidad (y, por lo tanto, debe iterar varias carpetas) o el usuario puede haber cambiado la carpeta. Un ejemplo extremo: la carpeta de elementos eliminados contiene elementos de correo entrante y saliente.

He elegido una solución similar a la de otra persona (Adi Kini) de arriba donde controlo ReceivedByName (creo que eligió ReceivedEntryID). La propiedad ReceivedByName siempre es nula ("") para un mensaje enviado, donde sea que se encuentre actualmente. Este método puede encontrar un elemento enviado que se ha arrastrado a la bandeja de entrada !. Parece un método bastante confiable para verificar.

Parece extraño que algo tan sencillo como comprobar si el correo es entrante o saliente puede hacernos tropezar.

+0

Tenga en cuenta que ni 'ReceivedByName' ni' ReceivedEntryID' tendrán un valor si el elemento de correo fue recibido por una carpeta pública que tiene una dirección asignada. – cremor

0

Para un simple control enviado/recibido por dirección SMTP, sugiero un enfoque de verificación de dirección. Se puede hacer de esta manera:

'Get mail address sender 
     Dim mailSender As String = GetSenderSMTPAddress(outMailItem) 

'Get current user mail address 
     Dim mailUser As String = OutlookMail2DocScriba.GetUserSMTPAddress(oNameSpace.CurrentUser.AddressEntry) 

     'If sender and current user matches is a sended mail, otherwise received 
     If String.Compare(mailSender, mailUser, True) = 0 Then 
      Return "Sended" 
     Else 
      Return "Received" 
     End If 





    Public Shared Function GetSenderSMTPAddress(ByVal mail As Outlook.MailItem) As String 
      'http://msdn.microsoft.com/en-us/library/microsoft.office.interop.outlook.oladdresslisttype.aspx 

      If mail Is Nothing Then 
       Throw New ArgumentNullException() 
      End If 
      If mail.SenderEmailType = "EX" Then 
       Dim sender As Outlook.AddressEntry = Nothing 

       Try 
        sender = mail.Sender 
       Catch ex As Exception 
        'Se non è stato in grado di reperire il sender (Outlook 2007), 
        'ignoro l'eccezione e procedo. 
       End Try 

       If sender IsNot Nothing Then 
        Return GetUserSMTPAddress(sender) 
       Else 
        Return Nothing 
       End If 
      Else 
       Return mail.SenderEmailAddress 
      End If 
     End Function 

     Public Shared Function GetUserSMTPAddress(ByVal sender As Outlook.AddressEntry) As String 
      'Now we have an AddressEntry representing the Sender 
      'http://msdn.microsoft.com/en-us/library/office/ff868214(v=office.15).aspx 
      Const EXCHANGE_USER_ADDRESS_ENTRY As Int32 = 0 
      Const EXCHANGE_REMOTE_USER_ADDRESS_ENTRY As Int32 = 5 
      Dim PR_SMTP_ADDRESS As String = "http://schemas.microsoft.com/mapi/proptag/0x39FE001E" 

      If sender.AddressEntryUserType = EXCHANGE_USER_ADDRESS_ENTRY OrElse _ 
       sender.AddressEntryUserType = EXCHANGE_REMOTE_USER_ADDRESS_ENTRY Then 
       'Use the ExchangeUser object PrimarySMTPAddress 
       Dim exchUser As Object = sender.GetExchangeUser() 
       If exchUser IsNot Nothing Then 
        Return exchUser.PrimarySmtpAddress 
       Else 
        Return Nothing 
       End If 
      Else 
       Return TryCast(sender.PropertyAccessor.GetProperty(PR_SMTP_ADDRESS), String) 
      End If 
     End Function 
Cuestiones relacionadas