You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用PHPMailer、PHPSpreadsheet与DOMPdf时遇setPaper()方法未定义错误求助

解决Dompdf报错Call to undefined method Dompdf\Options::setPaper()及邮件发送问题

核心报错原因

Dompdf 2.0及以上版本已移除setPaper()方法,替代方案有两种:

  • 分别调用setDefaultPaperSize()设置纸张规格(如letter)和setDefaultPaperOrientation()设置纸张方向(如portrait)
  • 直接通过数组初始化Options对象

代码中的其他问题及修正

除了Dompdf的方法兼容问题,你的代码还有几处逻辑错误需要调整:

  1. PhpSpreadsheet生成PDF逻辑错误:错误调用了Dompdf的loadHtml方法,PhpSpreadsheet的Dompdf Writer会自动处理Excel转PDF,无需手动加载HTML
  2. PHPMailer循环重置问题:每次循环发送邮件后,未清除之前的收件人和附件,会导致后续邮件携带历史内容
  3. 变量未定义问题:邮件结果输出中的$to变量未定义,需替换为实际的会员邮箱

修正后的完整代码

require_once 'vendor/autoload.php';

use PhpOffice\PhpSpreadsheet\IOFactory;
use PhpOffice\PhpSpreadsheet\Writer\Pdf\Dompdf;
use Dompdf\Options;

use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\Exception;

// 获取表单提交的年份
$year = $_POST['year'];

// 获取对应年份的会员捐赠数据
$members = getMemberDonations($year);

// 初始化PHPMailer(移到循环外避免重复初始化)
$mail = new PHPMailer(true); // 启用异常处理便于调试
try {
    // 配置SMTP参数
    $mail->isSMTP();
    $mail->Host = 'smtp.gmail.com';
    $mail->SMTPAuth = true;
    $mail->Username = 'liccftest@gmail.com';
    $mail->Password = 'citgxpzhmtoticrv';
    $mail->SMTPSecure = 'tls';
    $mail->Port = 587;
    $mail->setFrom('liccftest@gmail.com', 'LICCF');

    // 邮件模板
    $body = 'Dear {first} {last},<br><br>' .
            'Thank you for your donation of ${amount} to LICCFTaxReceipt in {year}.<br>' .
            'Please find attached your tax receipt for this donation.<br><br>' .
            'Sincerely,<br>LICCFTaxReceipt Team';

    foreach ($members as $member) {
        $variables = [
            '{first}' => $member['f_name'],
            '{last}' => $member['l_name'],
            '{address}' => $member['address'],
            '{city}' => $member['city'],
            '{province}' => $member['province'],
            '{postal}' => $member['postal_code'],
            '{amount}' => $member['total_amount'],
            '{year}' => $year,
            '{email}' => $member['email'],
        ];

        // 加载Excel模板
        $spreadsheet = IOFactory::load('receipt template.xlsx');
        $worksheet = $spreadsheet->getActiveSheet();

        // 替换单元格变量
        foreach ($worksheet->getRowIterator() as $row) {
            foreach ($row->getCellIterator() as $cell) {
                $value = $cell->getValue();
                foreach ($variables as $variable => $replacement) {
                    $value = str_replace($variable, $replacement, $value);
                }
                $cell->setValue($value);
            }
        }

        // 配置Dompdf选项(二选一即可)
        // 方式一:数组初始化
        $options = new Options([
            'defaultPaperSize' => 'letter',
            'defaultPaperOrientation' => 'portrait'
        ]);
        // 方式二:调用新方法
        // $options = new Options();
        // $options->setDefaultPaperSize('letter');
        // $options->setDefaultPaperOrientation('portrait');

        // 初始化PhpSpreadsheet的Dompdf Writer并生成PDF
        $writer = new Dompdf($spreadsheet, $options);
        $pdfContent = $writer->getContent();

        // 保存PDF到磁盘(可选)
        $fileName = "LICCFTaxReceipt_{$member['f_name']}_{$member['l_name']}_{$year}.pdf";
        file_put_contents($fileName, $pdfContent);

        // 重置PHPMailer收件人和附件
        $mail->clearAddresses();
        $mail->clearAttachments();

        // 设置当前邮件信息
        $mail->addAddress($member['email']);
        $mail->Subject = "Tax Receipt for your donation to LICCFTaxReceipt for the year of {$year}";
        $mail->Body = str_replace(array_keys($variables), array_values($variables), $body);
        $mail->isHTML(true); // 启用HTML格式
        $mail->addStringAttachment($pdfContent, $fileName);

        // 发送邮件
        $mail->send();
        echo "Email sent successfully to {$member['email']}<br>";
    }
} catch (Exception $e) {
    echo "Mailer Error: {$mail->ErrorInfo}<br>";
} catch (\PhpOffice\PhpSpreadsheet\Exception $e) {
    echo "Spreadsheet Error: {$e->getMessage()}<br>";
} catch (\Dompdf\Exception $e) {
    echo "Dompdf Error: {$e->getMessage()}<br>";
}

关键修改说明

  1. Dompdf配置兼容:用新版本支持的方式设置纸张参数
  2. PDF生成逻辑修正:利用PhpSpreadsheet Writer的原生方法直接生成PDF内容
  3. PHPMailer循环清理:每次循环重置收件人和附件,避免内容混乱
  4. 异常捕获优化:覆盖邮件、表格、PDF生成三个环节的异常,便于定位问题
  5. 文件名优化:添加会员姓名避免文件覆盖

内容的提问来源于stack exchange,提问作者Donavon04

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.29 10:13:17