PHP 內建的 mail() 函數雖然方便,但若未妥善驗證使用者輸入,極易遭受郵件標頭注入攻擊。本文詳細解析攻擊原理與防禦策略。
典型的不安全郵件表單代碼:
<?php
if (isset($_REQUEST['email'])) {
$email = $_REQUEST['email'];
$subject = $_REQUEST['subject'];
$message = $_REQUEST['message'];
mail("admin@example.com", $subject, $message, "From: " . $email);
echo "郵件發送成功";
}
?>
攻擊者可在 email 欄位輸入惡意字串:
attacker@example.com%0ACc:victim1@example.com%0ABcc:victim2@example.com,victim3@example.com%0ATo:victim4@example.com
由於 %0A 為換行符 URL 編碼,mail() 會將其解析為多個郵件標頭,導致郵件被發送至攻擊者指定的所有地址,淪為垃圾郵件發送器。
核心原則:永遠不信任使用者輸入,嚴格驗證與過濾。
<?php
function spamCheck($field) {
// 移除非法字符
$field = filter_var($field, FILTER_SANITIZE_EMAIL);
// 驗證格式
if (filter_var($field, FILTER_VALIDATE_EMAIL)) {
return TRUE;
}
return FALSE;
}
if (isset($_REQUEST['email'])) {
$mailCheck = spamCheck($_REQUEST['email']);
if ($mailCheck === FALSE) {
echo "非法輸入";
} else {
$email = $_REQUEST['email'];
$subject = $_REQUEST['subject'];
$message = $_REQUEST['message'];
mail("admin@example.com", "Subject: $subject", $message, "From: $email");
echo "感謝使用我們的郵件表單";
}
}
?>
FILTER_SANITIZE_EMAIL 過濾FILTER_VALIDATE_EMAIL 驗證str_replace(["\r", "\n"], "", $subject)mail()郵件安全不僅關乎應用程式信譽,更關乎伺服器 IP 信譽與郵件送達率。建立多層防護,從輸入端阻絕風險,是每位 PHP 開發者的必修課。