无邮箱账户通过模拟身份发送带附件邮件的问题求助
这个错误的核心原因是:你使用的服务账户本身没有独立邮箱,当它通过模拟身份操作Exchange时,Exchange无法自动推断出要关联的目标邮箱(你的共享收件箱)上下文——尤其是在涉及到发件箱这类"特殊文件夹"的操作时,必须明确指定该文件夹所属的邮箱SMTP地址。
结合你的需求,我给你整理了修复后的代码和关键注意事项:
首先,必须先完成Exchange端的权限配置:让你的服务账户拥有共享收件箱的「Send As」权限(需要Exchange管理员在后台配置,配置后可能需要等待15-30分钟生效)。
然后修改代码如下:
var sharedMailboxSmtp = Resources.EmailUsername; var service = new ExchangeService { TraceEnabled = true }; // 配置服务账户的身份验证(根据你的实际认证方式调整,比如OAuth或账号密码) // 示例:如果使用账号密码认证(不推荐生产环境,优先OAuth) // service.Credentials = new NetworkCredential("你的服务账户用户名", "服务账户密码"); // 设置模拟身份为共享收件箱的SMTP地址 service.ImpersonatedUserId = new ImpersonatedUserId(ConnectingIdType.SmtpAddress, sharedMailboxSmtp); // 自动发现Exchange服务地址,使用共享收件箱的地址 service.AutodiscoverUrl(sharedMailboxSmtp, RedirectionUrlValidationCallback); // 创建邮件并显式指定发件人为共享收件箱 var email = new EmailMessage(service); email.From = new EmailAddress(sharedMailboxSmtp); // 添加收件人 if (!string.IsNullOrWhiteSpace(recipients)) { foreach (var recipient in recipients.Split(',')) { email.ToRecipients.Add(recipient.Trim()); } } email.Subject = subject; email.Body = new MessageBody(BodyType.HTML, body); // 添加附件(如果有) if (attachmentName != null && attachment != null) { email.Attachments.AddFileAttachment(attachmentName, attachment); } // 关键:发送邮件并将副本保存到共享收件箱的发件箱,明确指定目标邮箱 var sharedSentItemsFolder = new FolderId(WellKnownFolderName.SentItems, new Mailbox(sharedMailboxSmtp)); email.SendAndSaveCopy(sharedSentItemsFolder);
代码修改的关键点说明:
- 显式设置From地址:确保邮件从共享收件箱发出,避免Exchange默认使用服务账户(无邮箱)导致的上下文混乱
- 使用SendAndSaveCopy替代Send:通过指定共享收件箱的发件箱FolderId,明确告诉Exchange要操作的目标邮箱,解决错误提示中"必须指定邮箱SMTP地址"的问题
- 身份验证配置:不要漏掉服务账户的身份验证部分,根据你的Exchange环境选择合适的认证方式(现在Exchange Online推荐使用OAuth 2.0)
如果还是遇到权限问题,先检查服务账户的「Send As」权限是否生效,或者尝试使用「Send On Behalf Of」权限(不过前者更符合你的需求)。
内容的提问来源于stack exchange,提问作者Jean-Bernard Pellerin
相关产品推荐
相关产品推荐

