如何在没有邮箱的情况下使用带有windows身份验证和标识的EWS发送和保存电子邮件

本文关键字:身份验证 EWS 标识 电子邮件 保存 windows 情况下 | 更新日期: 2023-09-27 18:27:36

我的场景是:

  • 我使用服务帐户和windows身份验证连接到Exchange Web服务(EWS)
  • 我不使用模拟
  • 服务帐户没有邮箱
  • 我连接到邮箱"MyMailbox"以阅读和发送电子邮件。每当我发送电子邮件时,我都会使用SendAndSaveCopy(),指定MyMailbox的SentItems文件夹保存。如果不指定文件夹,SendAndSaveCopy()会失败,这是可以理解的,因为没有链接到我的服务帐户的邮箱可以保存电子邮件
  • 我有时想以其他用户的身份发送或代表其他用户发送,所以我将From属性设置为该用户的主SMTP地址

在这种情况下,在我发送带有附件的电子邮件之前,一切都很好。在这种情况下,ResponseCode = ErrorMissingEmailAddressMessageText = When making a request as an account that does not have a mailbox, you must specify the mailbox primary SMTP address for any distinguished folder Ids. 失败

查看从我的SendAndSaveCopy()发送的SOAP消息,我可以看到当我有一个附件时,它是完全不同的——注意MessageDisposition="SaveOnly"

  <?xml version="1.0" encoding="utf-8"?>
  <soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:m="http://schemas.microsoft.com/exchange/services/2006/messages" xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
    <soap:Header>
      <t:RequestServerVersion Version="Exchange2010_SP2" />
    </soap:Header>
    <soap:Body>
      <m:CreateItem MessageDisposition="SaveOnly">
        <m:Items>
          <t:Message>
            <t:Subject>My test email subject</t:Subject>
            <t:Body BodyType="HTML">....

而当在没有附件的情况下发送时,其具有CCD_。EWS先保存电子邮件,然后再发送,这似乎是合理的。事实上,API文档说

如果邮件包含未保存的附件,则此方法不起作用。在这种情况下,必须先保存消息,然后再发送。

虽然当我以具有邮箱的身份进行连接时,SendAndSaveCopy()似乎可以正常工作,MSDN示例代码显示调用SendAndSaveCopy()时没有任何临时步骤。该示例特别指出,SendAndSaveCopy()导致对EWS的三个调用:CreateItem、CreateAttachment和SendItem。

我的主要问题是:当我有附件时,我应该如何调用EWS来实现与SendAndSaveCopy()相同的事情?

第二个问题:这是一个bug吗?当给定文件夹ID时,SendAndSaveCopy()不应该使用该文件夹进行CreateItem调用吗?

我正在使用EWS 15.0.0.0并指定Exchange2010_SP2 api版本。

更新:

在进一步的检查中,我发现EWS管理的API也在有附件时为SendAndSaveCopy()发出多个EWS调用,并且我使用用户名&密码验证。我看到两条EWS消息:

  • 第一个具有CCD_ 15,并且显著地noCCD_ 16。那么它被保存在哪里了!?我的猜测是,它被保存到当前用户邮箱的默认位置,这在我的windows身份验证场景中失败了,因为没有当前用户的邮箱
  • 来自的响应提供了已保存邮件及其已保存附件的ItemId
  • 第二个EWS调用具有<m:SendItem SaveItemToFolder="true">,并且还设置SavedItemFolderId

我仍然觉得这是SendAndSaveCopy()中的一个bug或缺少的功能:它应该使用指定的文件夹位置来保存临时消息。但无论如何,我应该使用什么EWS托管API调用来获得所需的效果?

如何在没有邮箱的情况下使用带有windows身份验证和标识的EWS发送和保存电子邮件

第一个没有SavedItemFolderId。那么它被保存在哪里了!?我的猜测是,它被保存到当前用户邮箱的默认位置,这在我的windows身份验证场景中失败了,因为没有当前用户的邮箱。

默认保存位置是您正在使用的安全主体邮箱的草稿文件夹。EWS是一个客户端API,所以你看到的行为是围绕着你期望普通电子邮件客户端做的事情设计的

如果你想在没有中间步骤的情况下发送带有附件的消息,你可以用MIME编码你想用附件发送的消息,然后用一个电话发送,例如

EmailMessage test2 = new EmailMessage(service);
String bodyContent = "<html><head><meta http-equiv='"Content-type'" content='"text/html;charset=UTF-8'">Hello World</head><body></body></html> ";
CDO.Message msMessage = new CDO.Message();
msMessage.BodyPart.Charset = "UTF-8";
msMessage.HTMLBody = bodyContent;
msMessage.HTMLBodyPart.Charset = "UTF-8";
msMessage.AddAttachment("c:''temp''Document.docx");
ADODB.Stream asMessageStream = msMessage.GetStream();
asMessageStream.Type = ADODB.StreamTypeEnum.adTypeBinary;
byte[] bdBinaryData1 = new byte[asMessageStream.Size];
bdBinaryData1 = (byte[])asMessageStream.Read(asMessageStream.Size);
service.TraceEnabled = true;
test2.MimeContent = new MimeContent("UTF-8", bdBinaryData1);
test2.ToRecipients.Add("user@domain.com");
test2.Subject = "test";
test2.SendAndSaveCopy();

干杯Glen