为什么MailKit在Html正文中嵌入的图像也显示为附件?

问题描述 投票:0回答:1

当我尝试使用具有嵌入图像的 html 正文的 MailKit 发送邮件时,图像显示在电子邮件正文中,但也显示为附件。

why attachment

我不需要附件,只要像下面这样的邮件正文

no attachment

我的邮件正文组成的代码如下:

 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=['""]([^'""]+)['""][^>]*>"; // Regex to match <img> tags and extract src
     MatchCollection matches = Regex.Matches(input, pattern);

     foreach (Match match in matches)
     {
         string imgTag = match.Value;
         string srcValue = match.Groups[1].Value;

         // Check if src is base64
         if (srcValue.StartsWith("data:image/"))
         {
             // Extract base64 string
             string base64Data = srcValue.Substring(srcValue.IndexOf(",") + 1);
             string imageFormat = srcValue.Substring(5, srcValue.IndexOf(";") - 5); // Get image format (e.g., png, jpeg)

             // Convert base64 to linked resource and add to BodyBuilder
             byte[] imageBytes = Convert.FromBase64String(base64Data);
             var stream = new MemoryStream(imageBytes);

             var id = MimeUtils.GenerateMessageId();
             var newpart = new MimePart()
             {
                 ContentId = id,
                 Content = new MimeContent(stream),
                 ContentDisposition = new ContentDisposition(ContentDisposition.Inline),
                 ContentTransferEncoding = ContentEncoding.Base64
             };
             
             bodyBuilder.LinkedResources.Add(newpart);
             
             string newImgTag = $"<img src='cid:{id}' />"; 
            
             input = input.Replace(imgTag, newImgTag);
         }
     }
     bodyBuilder.HtmlBody = input;
     return bodyBuilder;
 }

我从编辑器获得的示例 MessageBody 是(为简洁起见,省略了完整图像字节)-

"<p>this is a image email</p>\n<p><img src=\"data:image/png;base64,iVBORw0KGgoA..."></p>

编辑:让它工作。更新后的代码发布在下面。

c# .net mailkit
1个回答
0
投票

我通过在 MimePart 构造函数中传递两个参数来使其工作,第一个是“图像”,第二个是我提取但未使用的图像格式。 我还注意到,在使用生成的 ContentId 创建新标签时,我完全替换了标签的其他属性,因此我也改进了该代码位。

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).Split('/')[1]; 

        byte[] imageBytes = Convert.FromBase64String(base64Data);
        var stream = new MemoryStream(imageBytes);

        var id = MimeUtils.GenerateMessageId();
        var newpart = new MimePart("image", imageFormat)
        {
            ContentId = id,
            Content = new MimeContent(stream),
            ContentDisposition = new ContentDisposition(ContentDisposition.Inline),
            ContentTransferEncoding = ContentEncoding.Base64
        };

        bodyBuilder.LinkedResources.Add(newpart);

        string newImgTag = Regex.Replace(imgTag, @"src=['""][^'""]+['""]", $"src='cid:{id}'");

        input = input.Replace(imgTag, newImgTag);
    }
}
bodyBuilder.HtmlBody = input;
return bodyBuilder;
}
© www.soinside.com 2019 - 2024. All rights reserved.