PHP邮件内嵌图片实现求助:图片无法正常显示问题
解决PHP邮件模板内嵌图片不显示的问题
好问题!你遇到的核心差异在于:直接通过邮件客户端插入图片时,图片是被内嵌到邮件内容里的,而你当前的PHP代码只是在HTML里引用了外部文件——要么是本地路径不对,要么是邮件客户端默认拦截了外部资源,所以图片显示不出来。要实现和手动插入一样的效果,我们需要把图片作为内嵌附件嵌入邮件中,具体做法如下:
方法一:内嵌图片(推荐,和手动插入效果一致)
我们需要构建一个多部分MIME邮件,将图片作为附件嵌入,并通过Content-ID在HTML中引用它。以下是完整的代码示例:
<?php $to = '收件人邮箱@example.com'; $subject = '带内嵌图片的邮件'; $from_email = '发件人邮箱@example.com'; // 图片路径(确保服务器能读取到这个文件) $image_path = 'link-image.jpg'; $image_filename = basename($image_path); // 获取图片的MIME类型 $mime_type = mime_content_type($image_path); // 读取图片内容并base64编码 $image_content = base64_encode(file_get_contents($image_path)); // 生成随机的MIME边界字符串 $boundary = uniqid('mixed_boundary_', true); // 设置邮件头 $headers = "From: $from_email\r\n"; $headers .= "MIME-Version: 1.0\r\n"; $headers .= "Content-Type: multipart/related; boundary=\"$boundary\"\r\n"; // 构建邮件内容 $message = "--$boundary\r\n"; $message .= "Content-Type: text/html; charset=UTF-8\r\n"; $message .= "Content-Transfer-Encoding: 7bit\r\n\r\n"; $message .= "<html><head></head><body>"; // 这里用cid:my_image来引用内嵌的图片,cid值要和附件里的Content-ID一致 $message .= "<img src='cid:my_image' alt='描述文本' /></body></html>\r\n\r\n"; // 添加图片附件部分 $message .= "--$boundary\r\n"; $message .= "Content-Type: $mime_type; name=\"$image_filename\"\r\n"; $message .= "Content-Disposition: inline; filename=\"$image_filename\"\r\n"; $message .= "Content-ID: <my_image>\r\n"; // 这里的ID要和HTML里的cid对应 $message .= "Content-Transfer-Encoding: base64\r\n\r\n"; $message .= $image_content . "\r\n\r\n"; // 结束边界 $message .= "--$boundary--"; // 发送邮件 mail($to, $subject, $message, $headers); ?>
关键说明:
multipart/related类型:告诉邮件客户端这是包含关联资源(HTML+内嵌图片)的多部分邮件Content-ID:给内嵌图片分配唯一ID,HTML中的img标签通过cid:ID来引用它,这样邮件客户端就会直接加载内嵌的图片,而不是去外部请求- Base64编码:邮件传输要求内容是7位ASCII,所以图片内容需要转成Base64格式
方法二:使用可访问的外部图片(不推荐)
如果你不想内嵌图片,也可以使用绝对URL引用图片,但要注意两点:
- 图片必须放在公开可访问的服务器上,比如
src="https://你的域名.com/link-image.jpg" - 大部分邮件客户端默认会阻止加载外部图片,用户需要手动允许才能看到,体验不如内嵌好
为什么你的原始代码不行?
你写的<img src='link-image.jpg'>用的是相对路径,邮件客户端无法识别这个路径(它不是在你的服务器上运行),所以找不到图片。即使换成绝对路径,也会被客户端拦截,这就是为什么手动插入能显示,而代码不行的原因。
内容的提问来源于stack exchange,提问作者ForTW
相关产品推荐
相关产品推荐

