需導出數據供 Excel 打開時,常見三種方案各有優劣。本文對比原生 Header 輸出 HTML 表格、CSV 格式、PhpSpreadsheet 庫,助你按場景選型。
header('Content-Type: application/vnd.ms-excel; charset=utf-8');
header('Content-Disposition: attachment; filename="report_' . date('Ymd') . '.xls"');
header('Pragma: no-cache');
header('Expires: 0');
echo "<table border='1'><tr><th>標題</th><th>關鍵詞</th><th>URL</th></tr>";
foreach ($rows as $row) {
echo "<tr><td>{$row['title']}</td><td>{$row['keywords']}</td><td>{$row['url']}</td></tr>";
}
echo "</table>";
header('Content-Type: text/csv; charset=UTF-8');
header('Content-Disposition: attachment; filename="report_' . date('Ymd') . '.csv"');
$out = fopen('php://output', 'w');
// 寫入 BOM 防止 Excel 打開中文亂碼
fprintf($out, chr(0xEF).chr(0xBB).chr(0xBF));
fputcsv($out, ['標題', '關鍵詞', 'URL']);
foreach ($rows as $row) {
fputcsv($out, [$row['title'], $row['keywords'], $row['url']]);
}
fclose($out);
\t 或 ' 強制文本)。composer require phpoffice/phpspreadsheet
use PhpOffice\PhpSpreadsheet\Spreadsheet;
use PhpOffice\PhpSpreadsheet\Writer\Xlsx;
$spreadsheet = new Spreadsheet();
$sheet = $spreadsheet->getActiveSheet();
$sheet->fromArray([['標題','關鍵詞','URL']], null, 'A1');
$sheet->fromArray($rows, null, 'A2');
// 樣式示例
$sheet->getStyle('A1:C1')->getFont()->setBold(true);
$sheet->getColumnDimension('A')->setWidth(40);
$writer = new Xlsx($spreadsheet);
header('Content-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet');
header('Content-Disposition: attachment; filename="report_' . date('Ymd') . '.xlsx"');
$writer->save('php://output');
PhpOffice\PhpSpreadsheet\Writer\Xlsx 的 setPreCalculateFormulas(false)、分塊寫入、或改用 Box\Spout(流式寫入庫)。| 場景 | 推薦方案 |
|---|---|
| 後台簡單導出 < 1 萬行、無樣式要求 | 方案一(HTML)或方案二(CSV) |
| 大數據導出 > 10 萬行、需流式寫入 | 方案二(CSV)或 Box/Spout |
| 客戶交付、複雜樣式、多 Sheet、公式 | 方案三 |
| 禁止安裝擴展/Composer 的受限環境 | 方案一 |
建議專案中封裝統一 ExcelExporter 介面,根據導出配置自動選擇最優策略,業務代碼零感知切換。