PHP表单不仅仅从移动设备发送信息

时间:2015-01-10 17:37:34

标签: php forms mobile

查看以下更新

我有这个非常简单的PHP联系表单,可以在每个浏览器上运行。在提交时,流程将通过formaction.php,您将在下面看到,然后验证验证码,发送信息并重定向到所选页面。

我的问题是,我上周意识到,在iPhone 4S,5S和三星SIII上测试时,表格在移动设备上使用时不会发送任何内容。

乍一看,我删除了$recipient变量,这是我对formaction.php所做的最后一次更新,并意识到问题不存在。

由于我是PHP的新手,我认为可能某些移动设备可能无法识别头部变量,所以我删除了$POST[blablabla]来编写一些核心信息。哪个没有用。

我经常搜索以查找移动和网络发送流程之间的差异,但问题仍然存在。

session_start();
if(isset($_POST["captcha"]) && 
   $_POST["captcha"]!="" && 
   $_SESSION["code"]==$_POST["captcha"])
{
    Header("Location: http://www.mysite.fake/thank" );

    $recipients = array('info' => 'info@mysite.fake', 
                        'ventes' => 'ventes@mysite.fake', 
                       'commandites' => 'commandites@mysite.fake'
                      );

    $to = $recipients[$_POST['sujet']];
    $head .= "From: ".$_POST['nom']." <".$_POST['courriel'].">\r\n";
    $head .= "X-Sender: <info@mysite.fake>\n";
    $head .= "X-Mailer: PHP\n";
    $head .= "Return-Path: <info@mysite.fake>\n";
    $head .= "Content-Type: text/plain; charset=utf-8\n";

    $sujet = "Subject | ".$_POST['nom']." contacted you for ".$_POST['sujet'].".";
    $informations = "
    Hi, you received a new demand. \r\n
    Name: ".$_POST['nom']." \r\n
    Mail: ".$_POST['courriel']." \r\n
    Subject: ".$_POST['sujet']."\r\n
    Message: ".$_POST['texte']." \r\n";

    mail($to, $sujet ,$informations, $head); 
} else {
    Header("Location: http://www.mysite.fake/error" );
}

更新:在与@RiggsFolly交谈后,我验证了Apache日志,并且请求确实正常到达服务器。所以,一切都在后端......任何想法?

[10/Jan/2015:19:58:45 -0700] "GET /fr/contact HTTP/1.1" 200 3997 "-" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"
[10/Jan/2015:19:58:45 -0700] "GET /fr/captcha/captcha.php HTTP/1.1" 200 588 "http://eragraff.com/fr/contact" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"
[10/Jan/2015:19:59:19 -0700] "POST /fr/formaction.php HTTP/1.1" 302 547 "http://eragraff.com/fr/contact" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"
[10/Jan/2015:19:59:22 -0700] "GET /fr/formthank HTTP/1.1" 301 522 "http://eragraff.com/fr/contact" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"
[10/Jan/2015:19:59:23 -0700] "GET /fr/formthank HTTP/1.1" 200 682 "http://eragraff.com/fr/contact" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"
[10/Jan/2015:19:59:26 -0700] "GET /fr/contact HTTP/1.1" 200 3997 "http://eragraff.com/fr/formthank" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"
[10/Jan/2015:19:59:26 -0700] "GET /fr/captcha/captcha.php HTTP/1.1" 200 609 "http://eragraff.com/fr/contact" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"

Chrome桌面日志

184.xxx.xx.xx - - [10/Jan/2015:20:39:15 -0700] "POST /formaction.php HTTP/1.1" 302 430 "http://mysite.fake/contact" "Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/39.0.2171.95 Safari/537.36"

Safari移动日志

207.xx.xx.xxx - - [10/Jan/2015:20:28:29 -0700] "POST /formaction.php HTTP/1.1" 302 482 "http://mysite.fake/contact" "Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) Version/8.0 Mobile/12B440 Safari/600.1.4"

请求日志,使用* Charles Proxy

进行验证

这是请求;

POST /formaction.php HTTP/1.1
Host: mysite.fake
Content-Length: 141
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8,image/webp
Content-Type: application/x-www-form-urlencoded
Origin: http://mysite.fake
Referer: http://mysite.fake/contact
User-Agent: Mozilla/5.0 (iPhone; CPU iPhone OS 8_1_2 like Mac OS X) AppleWebKit/600.1.4 (KHTML, like Gecko) CriOS/39.0.2171.50 Mobile/12B440 Safari/600.1.4
Accept-Encoding: gzip, deflate
Accept-Language: fr-FR,fr;q=0.8,en-US;q=0.6,en;q=0.4
Cookie: __utma=113777771.1205974649.1111957503.1428078344.1426693544.35; __utmz=113777771.1111957503.1.1.utmcsr=(direct)|utmccn=(direct)|utmcmd=(none); __utmc=113777771; PHPSESSID=brmpaudvr2rxxxxxxxxna0000; __utmb=113777771.3.10.1421093598

这是服务器响应;

HTTP/1.1 302 Moved Temporarily
Date: Mon, 12 Jan 2015 20:34:40 GMT
Server: Apache
Expires: Thu, 19 Nov 1981 08:52:00 GMT
Cache-Control: no-store, no-cache, must-revalidate, post-check=0, pre-check=0
Pragma: no-cache
Location: http://mysite.fake/formthank
Vary: Accept-Encoding
Content-Encoding: gzip
Content-Length: 20
Content-Type: text/html

2 个答案:

答案 0 :(得分:0)

对我的代码进行疑难解答后,我意识到$head行确实存在问题。

特别是这个..

$head = "From: ".$_POST['nom']." <".$_POST['courriel'].">\n";

我测试从$head行删除mail后,我成功通过移动设备发送邮件。所以我逐一拿出每一行并编写了核心信息,它与第一个一起工作,From:,在那里我写了一个核心电子邮件地址。

$head = "From: <info@mysite.fake>\n";

嗯,问题解决了,另一个问题了。在From:中使用变量非常酷,因为它会将回复固定在用户身上。

如果有人知道为什么$_POST$head的{​​{1}}没有被移动设备同化,或者我怎样才能更好地实现它们,我会很高兴知道更多发生了什么事。

答案 1 :(得分:0)

您的问题实际上是由巧合引起的,与您提交表单的设备无关。问题是您的代码将发件人地址设置为用户在表单中提交的任何电子邮件,并且您的邮件服务器拒绝该邮件服务器,因为发件人地址显然与您的脚本用于登录SMTP服务器的凭据不匹配

不要将发件人的地址欺骗到客户输入的地址,而是使用服务器接受的发件人地址,例如contactform@yourdomain,并将Reply-To标头设置为客户&#39 ; s电子邮件,所以你仍然保留欺骗发件人地址的所有好处(我假设它能够通过点击&#34;回复&#34;在你的邮件客户端中直接回复客户)让服务器感到高兴,因为你不会欺骗任何东西。这是一个例子:

$mail->From = "contactform@yourdomain"; // no sender spoofing so server is happy
$mail->addReplyTo("customer's email", "customer's name"); // reply button works

此外,您当前的代码有一些问题,没有对数据进行验证(我可以提交空值,您的脚本仍会尝试发送邮件),没有错误检查(您立即将用户重定向到成功页面甚至在尝试发送邮件之前)和电子邮件标题注入(攻击者可以使用您的服务器向任何地址发送垃圾邮件)。

首先,我建议您使用PHPMailer代替mail(),使用起来要轻松得多,您不必手动构建标题字符串,而是“#{}}这是安全的电子邮件注入。

这是我提出的一个基本脚本,它绝对不是我编写过的最漂亮的代码,但它在验证值方面做得非常好,如果有的话会抛出有意义的错误是错的:

session_start();

// iterate over all expected values and exit if any are missing or empty
foreach (["captcha", "sujet", "nom", "courriel", "texte"] as $value) {
    if (!isset($_POST[$value]) || empty($_POST[$value])) {
        die("Missing or empty value ".$value);
    }
}

// recipient array, used both for validation and mail sending
$recipients = ["info" => "info@...", "ventes" => "ventes@...", "commandites" => "..."];

// exit if the recipient's identified isn't valid
if (!in_array($_POST["sujet"], array_keys($recipients))) {
    die("Incorrect recipient");
}

// exit if the sender's email address isn't valid
if (!filter_var($_POST["courriel"], FILTER_VALIDATE_EMAIL)) {
    die("Incorrect sender email");
}

// check if the captcha's code was set previously
if (!isset($_SESSION["code"])) {
    // if not, ask the user to go back and see the captcha
    die("Missing code, go back and request the captcha image again");
} elseif ($_SESSION["code"] != $_POST["captcha"]) {
    // otherwise, check if the captcha is correct and exit if not
    die("Incorrect captcha, please try again");
}

// new mailer object
$mail = new PHPMailer;

// configure your SMTP server's details
$mail->isSMTP();
$mail->Host = "smtp.example.com";
$mail->Port = 25; // 587 for tls (STARTTLS), 465 for ssl

// if your server requires auth
$mail->SMTPAuth = true;
$mail->Username = "user@example.com";
$mail->Password = "secret";
$mail->SMTPSecure = "tls";

// here we make the actual email
$mail->From = "contactform@yourdomain";
$mail->FromName = $_POST["nom"];
$mail->addAddress($recipients[$_POST["sujet"]]);
$mail->addReplyTo($_POST["courriel"], $_POST["nom"]);
$mail->Subject = $_POST["sujet"];
$mail->Body = $_POST["texte"];

if ($mail->send()) {
    echo "Success !";
} else {
    echo "Something went wrong";
    echo "Error details :".$mail->ErrorInfo;
    // in production, hide the error details to not reveal potentially sensitive info
}