使用 PHPMailer 在 PHP 中发送电子邮件
PHPMailer 可能是最流行的用于发送电子邮件的开源 PHP 库。 它于 2001 年首次发布,从那时起,它已成为 PHP 开发人员最喜欢的以编程方式发送电子邮件的方式,除了 Swiftmailer 等其他一些粉丝最喜欢的方式之外。
在本文中,我们将讨论为什么您应该使用 PHPMailer 而不是 PHP 的 mail()
函数,我们将展示一些关于如何使用这个库的代码示例。
它是 PHP 的替代品吗 mail()
功能?
在大多数情况下,它是 PHP 的替代品 mail()
功能,但还有许多其他情况下 mail()
功能不够灵活,无法实现您的需求。
首先,PHPMailer 提供了一个面向对象的接口,而 mail()
不是面向对象的。 PHP 开发人员通常讨厌创建 $headers
使用发送电子邮件时的字符串 mail()
功能,因为它们需要大量转义。 PHPMailer 使这变得轻而易举。 开发人员在使用 mail()
功能,而 PHPMailer 使这变得轻松。
此外, mail()
功能需要一个本地邮件服务器来发送电子邮件,这并不总是很容易设置。 如果您有身份验证,PHPMailer 可以使用非本地邮件服务器 (SMTP)。
其他优势包括:
- 发送邮件失败时,可以打印40多种语言的各种错误信息。 它通过 SSL 和 TLS 集成了 SMTP 协议支持和身份验证。 它可以为非 HTML 电子邮件客户端发送电子邮件的替代纯文本版本。 它有一个非常活跃的开发人员社区,可以保证它的安全和最新。
PHPMailer 也被流行的 PHP 内容管理系统使用,如 WordPress、Drupal 和 Joomla。
安装 PHPMailer
您可以使用 Composer 安装 PHPMailer:
composer require phpmailer/phpmailer
使用 PHPMailer 从本地 Web 服务器发送电子邮件
下面是使用 PHPMailer 从本地 Web 服务器发送电子邮件的最简单示例:
<?php
use PHPMailerPHPMailerPHPMailer;
use PHPMailerPHPMailerException;
require_once "vendor/autoload.php";
//PHPMailer Object
$mail = new PHPMailer(true); //Argument true in constructor enables exceptions
//From email address and name
$mail->From = "[email protected]";
$mail->FromName = "Full Name";
//To address and name
$mail->addAddress("[email protected]", "Recepient Name");
$mail->addAddress("[email protected]"); //Recipient name is optional
//Address to which recipient will reply
$mail->addReplyTo("[email protected]", "Reply");
//CC and BCC
$mail->addCC("[email protected]");
$mail->addBCC("[email protected]");
//Send HTML or Plain Text email
$mail->isHTML(true);
$mail->Subject = "Subject Text";
$mail->Body = "<i>Mail body in HTML</i>";
$mail->AltBody = "This is the plain text version of the email content";
try {
$mail->send();
echo "Message has been sent successfully";
} catch (Exception $e) {
echo "Mailer Error: " . $mail->ErrorInfo;
}
代码和注释应该足够清晰以解释正在发生的一切。
发送带附件的电子邮件
以下是如何使用 PHPMailer 发送带附件的电子邮件的示例:
<?php
use PHPMailerPHPMailerPHPMailer;
use PHPMailerPHPMailerException;
require_once "vendor/autoload.php";
$mail = new PHPMailer;
$mail->From = "[email protected]";
$mail->FromName = "Full Name";
$mail->addAddress("[email protected]", "Recipient Name");
//Provide file path and name of the attachments
$mail->addAttachment("file.txt", "File.txt");
$mail->addAttachment("images/profile.png"); //Filename is optional
$mail->isHTML(true);
$mail->Subject = "Subject Text";
$mail->Body = "<i>Mail body in HTML</i>";
$mail->AltBody = "This is the plain text version of the email content";
try {
$mail->send();
echo "Message has been sent successfully";
} catch (Exception $e) {
echo "Mailer Error: " . $mail->ErrorInfo;
}
在这里,我们附加了两个文件—— file.txt
,它与脚本位于同一目录中,并且 images/profile.png
,它位于 images
脚本目录的目录。
要向电子邮件添加附件,我们只需要调用该函数 addAttachment
通过将文件路径作为参数传递给 PHPMailer 对象。 对于附加多个文件,我们需要多次调用它。
故障排除
在我们的两个示例中,我们使用 PHPMailer 的 Exception 类进行调试,因此抛出的任何错误都将帮助我们调试可能发生的任何问题。 我们还添加了参数 true
到 PHPMailer 构造函数,以输出更高级别、更具描述性的异常。
根据我们使用的系统,我们看到的最常见的错误可能与运行 mail()
后台功能:
邮件程序错误:无法实例化邮件功能。
如果我们需要有关错误的更多详细信息,我们还可以在 catch 子句中添加如下内容:
print_r(error_get_last());
通常,邮件功能的问题与缺少邮件服务器设置有关,在这种情况下 error_get_last
函数将返回如下内容:
Array (
[type] => 2
[message] => mail(): Failed to connect to mailserver at "localhost" port 25, verify your "SMTP" and "smtp_port" setting in php.ini or use ini_set()
[file] => OUR_PATH vendorphpmailerphpmailersrcPHPMailer.php
[line] => 863
)
这是我们可能最常遇到的问题,我们可以使用 SMTP 轻松解决。
显示本地化错误消息
$mail->ErrorInfo
可以用 43 种不同的语言返回错误消息。
要以不同的语言显示错误消息,请复制 language
从 PHPMailer 的源代码目录到项目目录。
例如,要以俄语返回错误消息,请使用以下方法调用将 PHPMailer 对象设置为俄语:
$mail->setLanguage("ru");
您还可以将自己的语言文件添加到 language
目录。
使用 SMTP
您可以使用另一台主机的邮件服务器发送电子邮件,但为此您首先需要进行身份验证。 例如,要从 Gmail 的邮件服务器发送电子邮件,您需要有一个 Gmail 帐户。
SMTP 是邮件客户端用来向邮件服务器发送电子邮件发送请求的协议。 邮件服务器验证电子邮件后,会将其发送到目标邮件服务器。
下面是从您的域从 Gmail 的邮件服务器发送电子邮件的示例。 您不需要本地邮件服务器来运行代码。 我们将使用 SMTP 协议:
<?php
use PHPMailerPHPMailerPHPMailer;
use PHPMailerPHPMailerSMTP;
use PHPMailerPHPMailerException;
require_once "vendor/autoload.php";
$mail = new PHPMailer(true);
//Enable SMTP debugging.
$mail->SMTPDebug = 3;
//Set PHPMailer to use SMTP.
$mail->isSMTP();
//Set SMTP host name
$mail->Host = "smtp.gmail.com";
//Set this to true if SMTP host requires authentication to send email
$mail->SMTPAuth = true;
//Provide username and password
$mail->Username = "[email protected]";
$mail->Password = "super_secret_password";
//If SMTP requires TLS encryption then set it
$mail->SMTPSecure = "tls";
//Set TCP port to connect to
$mail->Port = 587;
$mail->From = "[email protected]";
$mail->FromName = "Full Name";
$mail->addAddress("[email protected]", "Recepient Name");
$mail->isHTML(true);
$mail->Subject = "Subject Text";
$mail->Body = "<i>Mail body in HTML</i>";
$mail->AltBody = "This is the plain text version of the email content";
try {
$mail->send();
echo "Message has been sent successfully";
} catch (Exception $e) {
echo "Mailer Error: " . $mail->ErrorInfo;
}
Gmail 需要通过 SMTP 进行 TLS 加密,因此我们对其进行了相应设置。 在通过 SMTP 发送之前,您需要找出主机名、端口号、加密类型(如果需要),如果需要身份验证,您还需要用户名和密码。 请注意,在 Gmail 上启用双因素身份验证不会让您使用带有用户名/密码的 SMTP。 相反,将需要额外的配置。
使用远程 SMTP 而不是本地邮件的一大优势是,如果您使用 PHP 的 mail()
发送电子邮件的功能 from
地址域设置为本地域名(服务器名称)以外的任何内容,则收件人的电子邮件服务器的攻击过滤器会将其标记为垃圾邮件。 例如,如果您从具有实际主机名的服务器发送电子邮件 example.com
与 from
地址 [email protected]
到 [email protected]
,然后雅虎的服务器会将其标记为垃圾邮件或向用户显示一条消息,要求用户不要信任该电子邮件,因为邮件的来源是 example.com
然而它却表现得好像来自 gmail.com
. 虽然你拥有 [email protected]
雅虎无法发现这一点。
使用 POP3 检索电子邮件
PHPMailer 还允许 POP-before-SMTP 验证来发送电子邮件。 换句话说,您可以使用 POP 进行身份验证并使用 SMTP 发送电子邮件。 遗憾的是,PHPMailer 不支持使用 POP3 协议从邮件服务器检索电子邮件。 它仅限于发送电子邮件。
结论
如果您是 PHP 开发人员,则几乎不可能避免以编程方式发送电子邮件。 虽然您可能会选择 Mandrill 或 SendGrid 等第三方服务,但有时这不是一个选项,而滚动您自己的电子邮件发送库更是如此。 这就是 PHPMailer 及其替代品(Zend Mail、Swift Mailer 等)的用武之地。
您可以在存储库 wiki 或官方文档中了解此库的 API。
您是否被 PHP 库依赖项所困扰? 观看我们的截屏视频,了解 Composer 如何帮助您管理它。