You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多
文档控制台
免费开始使用

使用FluentEmail发送邮件时无法嵌入图片的问题求助

解决FluentEmail内嵌图片无法显示的问题

我之前也踩过这个坑,用FluentEmail发内嵌图片时死活显示不出来,看了你的代码和模板后,发现几个关键问题,调整后就能正常显示了:

问题根源分析

你已经设置了IsInline = true,但没给内嵌图片指定唯一的ContentId——邮件客户端是通过cid:标识来匹配对应的图片资源的,光靠文件名根本找不到;另外手动处理流的方式也容易出问题,比如没正确释放资源或者流指针位置不对。

修正后的代码

using FluentEmail.Core;
using FluentEmail.Razor;
using FluentEmail.Smtp;
using System;
using System.IO;
using System.Net.Mail;

namespace FluentEmail
{
    public class EmailNotification : IEmailNotification
    {
        public bool SendEmailNotification()
        {
            try
            {
                // 配置SmtpClient
                var smtpClient = new SmtpClient
                {
                    Host = "smtp.office365.com",
                    Port = 587,
                    EnableSsl = true,
                    Credentials = new System.Net.NetworkCredential("username", "Password")
                };

                // 初始化FluentEmail默认发送器和渲染器
                Email.DefaultSender = new SmtpSender(smtpClient);
                Email.DefaultRenderer = new RazorRenderer();

                // 图片路径
                string imagePath = @"C:\Users\pratik.soni\Downloads\FluentLogo.png";
                // 生成唯一ContentId(用GUID避免多图片冲突)
                string imageContentId = $"fluent-logo-{Guid.NewGuid():N}";

                // 优化流处理:用File.ReadAllBytes+MemoryStream替代手动FileStream,避免资源泄漏
                var imageBytes = File.ReadAllBytes(imagePath);

                var inlineAttachment = new Core.Models.Attachment
                {
                    Data = new MemoryStream(imageBytes),
                    ContentType = "image/png",
                    Filename = "FluentLogo.png",
                    IsInline = true,
                    ContentId = imageContentId // 核心:设置ContentId,和cid对应
                };

                // 构建邮件,注意cid要和ContentId完全匹配
                var email = Email
                    .From("pratik.soni@1rivet.com")
                    .To("pratik.soni10@gmail.com")
                    .Subject("Test")
                    .Body($"<html>Inline image here: <img src=\"cid:{imageContentId}\">" +
                          "<p>You should see an image without an attachment, or without a download prompt, depending on the email client.</p></html>", true);

                email.Attach(inlineAttachment);
                email.Send();

                return true;
            }
            catch (Exception ex)
            {
                // 建议这里加日志记录,方便排查问题
                // Logger.LogError(ex, "发送内嵌图片邮件失败");
                return false;
            }
        }
    }
}

关键修改点说明

  • 添加ContentId属性:这是内嵌图片能被识别的核心,邮件客户端通过cid:xxx来匹配对应的附件资源,必须保证img标签的src和附件的ContentId完全一致。
  • 优化流处理:用File.ReadAllBytes结合MemoryStream替代手动打开FileStream,既避免了流未关闭的资源泄漏问题,也省去了手动调整流指针的麻烦。
  • 唯一ContentId:用GUID生成唯一标识,避免同时内嵌多张图片时出现ID冲突。

HTML模板中的图片引用调整

如果用Razor模板,需要动态绑定ContentId,比如:

<!-- Razor模板示例 -->
<img src="cid:@Model.ImageContentId" alt="FluentLogo" />

如果是静态HTML,直接写死对应的ContentId即可(但动态生成更灵活)。

额外注意事项

  • 部分邮件客户端(比如Outlook)默认会屏蔽内嵌图片,需要用户手动开启显示,但代码层面已经做了正确的内嵌配置。
  • 确保程序有读取图片文件的权限,路径不要写错。

内容的提问来源于stack exchange,提问作者I Love Stackoverflow

火山引擎 最新活动