3

我正在制作一个表单,我想让提交的 PHP 页面只有在提交表单时才可访问,从而防止对我的 PHP 页面的自定义请求。

这是我的 form.html:

<html>
    <head>
        <title>Name/Surname form</title>
    </head>
    <body>
        <form id="form1" method="POST" action="processData.php">
            Name: <input type="text" id="name" name="name"><br>
            Surname: <input type="text" id="surname" name="surname"><br>
            <input type="submit" value="Submit form">
        </form>
    </body>
</html>

然后是我的 processData.php:

<?php
    if(!isset($_POST['name'],$_POST['surname'])) die;

    include ("config.php");

    //connect
    $mysqli = new mysqli($dbhost, $dbuser, $dbpassword, $dbname); //variables from config.php

    //check connection
    if (mysqli_connect_errno()) {
        printf("Connect failed: %s\n", mysqli_connect_error());
        exit();
    }


    if ($stmt = $mysqli->prepare("INSERT INTO name_surname_table (name, surname) values (?, ?)")) {

        //bind
        $stmt->bind_param('ss', $name, $surname);

        //set
        $name=$_POST['name'];
        $surname=$_POST['surname'];

        //execute
        $stmt->execute();

        //close
        $stmt->close();
        }
    else {
        //error
        printf("Prepared Statement Error: %s\n", $mysqli->error);
    }
?>

问题是,如果我在未在上一页中提交表单的情况下进行自定义发布请求,则数据将提交到数据库,这意味着自动化程序可以将它想要的任何内容放入我的数据库中......我该如何防止这?

谢谢!

4

4 回答 4

4

您有很多选项可以阻止机器人自动提交您的表单:

  1. 使用验证或一些简单的计算字段(例如What gives 3 + 2 ?

  2. 用令牌

  3. 对$_REQUEST变量进行一些检查

令牌可以这样完成:

session_start();
//generate a unique string
$token = uniqid(rand(), true);
//Store the token
$_SESSION['token'] = $token;
//Store the token_time
$_SESSION['token_time'] = time();

在表单中添加隐藏输入:

<input type="hidden" name="token" id="token" value="<?php echo $token;?>"/>

与将表单提交到数据库之前相比:

session_start();
//If token exists
if(isset($_SESSION['token']) && isset($_SESSION['token_time']) && isset($_POST['token']))
{
    //If it's the same as the posted one
    if($_SESSION['token'] == $_POST['token'])
    {
        //For example 15 mins ago
        $old_time = time() - (15*60);
        //If token hasn't expired
        if($_SESSION['token_time'] >= $old_time)
        {
           //Do your queries here
        }
    }
}
于 2013-03-16T11:26:05.987 回答
1

从根本上说,您无法阻止恶意客户端向您的服务器发送“不正确”的数据。由您来检测这种情况并适当地处理错误情况。

如果只有某些用户应该能够提交数据,那么显然您需要某种形式的登录系统。然后,您可以信任来自登录用户的任何数据,并拒绝其他所有数据。

如果您只想知道客户端在前一页加载了表单,您可以添加一个包含“nonce”的隐藏字段 - 一个随机字符串,您将其值存储在服务器上的某处,例如 PHP 会话中。如果提交的随机数与预期值不匹配,则拒绝输入。请注意,这并不能保证用户在他们的浏览器中与表单进行了交互,只保证他们下载了它(因为程序仍然可以提取随机数并刺激提交表单)

于 2013-03-16T11:36:49.593 回答
0

您可能在表单中有一个隐藏字段,其中包含过期的密码......

当您生成表单时,您可以通过在时间上运行哈希甚至只是选择一个随机数来计算代码。然后将其存储在您的会话中并将其插入您发送的表单中。

处理表单提交时,请检查以确保密码与会话中存储的密码相同。

于 2013-03-16T11:31:11.047 回答
0

您应该为您的表单进行基于令牌的身份验证。

在显示表单的页面中,首先使用随机代码设置会话变量。

//generate this using whatever random code generation method you prefer.
$_SESSION["token"] = "your-random-code";

在您的论坛中有一个隐藏字段,如下所示。

<input type="hidden" name="token" value="<?php echo $_SESSION['token'] ?>">

在提交处理程序 php 文件中,进行如下检查。

if(isset($_POST['token']) && $_POST['token'] == $_SESSION['token'])
于 2013-03-16T11:34:10.147 回答