使用MailKit发送含内嵌图片的HTML邮件,图片为何同时显示为附件?
解决MailKit内嵌图片同时显示为附件的问题
问题场景
使用MailKit发送带内嵌图片的HTML邮件时,图片能正常显示在正文,但会被额外当作附件展示。需要实现图片仅作为正文内容存在,不显示为附件的效果。
原代码问题分析
原代码中手动创建MimePart并添加到LinkedResources时,存在字符串拼接语法错误,且资源的MIME属性处理不够严谨,导致邮件客户端将内嵌资源识别为附件。
修复后的代码
private async Task<MimeMessage> MailCompose(Command request) { var to = request.EmailAddresses.Select(x => MailboxAddress.Parse(x)); var message = new MimeMessage(); message.From.Add(MailboxAddress.Parse(request.MailSettingsRequest.SMTPEmailID)); message.To.AddRange(to); message.Subject = request.EmailTemplateRequest.TemplateSubject; message.Body = UpdateImageTags(request.EmailTemplateRequest.MessageBody).ToMessageBody(); return message; } static BodyBuilder UpdateImageTags(string input) { var bodyBuilder = new BodyBuilder(); string pattern = @"<img[^>]*\s+src=['""]([^'""]+)['""][^>]*>"; MatchCollection matches = Regex.Matches(input, pattern); foreach (Match match in matches) { string imgTag = match.Value; string srcValue = match.Groups[1].Value; if (srcValue.StartsWith("data:image/")) { string base64Data = srcValue.Substring(srcValue.IndexOf(",") + 1); string imageFormat = srcValue.Substring(5, srcValue.IndexOf(";") - 5); byte[] imageBytes = Convert.FromBase64String(base64Data); var stream = new MemoryStream(imageBytes); var cid = MimeUtils.GenerateMessageId(); // 通过BodyBuilder添加内嵌资源,自动处理MIME属性 var linkedResource = bodyBuilder.LinkedResources.Add($"image.{imageFormat}", stream); linkedResource.ContentId = cid; linkedResource.ContentDisposition = new ContentDisposition(ContentDisposition.Inline); // 替换原img标签为cid引用 string newImgTag = $"<img src='cid:{cid}' />"; input = input.Replace(imgTag, newImgTag); } } bodyBuilder.HtmlBody = input; return bodyBuilder; }
关键修复点
- 修正了原代码中
newImgTag字符串未闭合引号的语法错误 - 使用
BodyBuilder.LinkedResources.Add方法添加资源,让框架更合理地处理资源的MIME配置 - 显式设置
ContentDisposition为Inline,明确标记资源为内嵌内容,避免被识别为附件 - 确保生成的
ContentId与HTML中的cid:引用一一对应,保证图片能正确嵌入正文
内容的提问来源于stack exchange,提问作者Muheeb
相关产品推荐
相关产品推荐

