因此,对于学校项目,我必须使用登录系统创建一个站点。它有一个用户名和密码字段,以及一个提交按钮。它将用户名和密码与MySQL数据库中的用户名和密码进行比较。如果组合在数据库中,则用户可以继续,否则将重定向到登录页面。我使用准备好的PDO语句进行数据库连接。
现在我的老师要我通过在登录系统上执行sql攻击来测试安全性。不幸的是,我不知道在这些盒子里放什么,结果会是什么。例如,我已经尝试在用户名和密码字段中输入值将返回true,如下所示:
1==1, 1===1, 0 is null
但我不知道我是否成功,攻击者是否可以通过这些语句访问或截断我的数据库。
Html代码:
<form method="post" action="includes/login.php">
<input type="text" name="gebruikersnaam" >
<input type="password" name="wachtwoord" >
<input type="submit" value="login">
</form>
Php身份验证:
$myusername=$_POST['gebruikersnaam'];
$mypassword=$_POST['wachtwoord'];
$sql="SELECT * FROM leerling WHERE leerlingnummer='$myusername' and wachtwoord='$mypassword'";
$sql2="SELECT * FROM lop WHERE gebruikersnaam='$myusername' and wachtwoord='$mypassword'";
$statement2=$conn->prepare($sql2);
$statement2->execute();
$count2=$statement2->rowcount();
if($count2==1){proceed}
$statement = $conn->prepare($sql);
$statement->execute();
$count= $statement->rowcount();
if($count==1){proceed}
else {deny access}
答案 0 :(得分:1)
想象一下这个问题:
SELECT id FROM users WHERE email=? AND password=? LIMIT 1
现在假设值为foo@bar.hello
,password
为空字符串:
SELECT id FROM users WHERE email='foo@bar.hello' AND password='' LIMIT 1
如果这些凭据不在您的数据库中,那么这将不会有害。现在让我们给出不同的输入:
对于email
我们填写一个空字符串,对于password
我们插入' OR 1=1
(注意第一个撇号)
您的老师希望您了解这是否意味着您的SQL服务器将执行以下查询:
SELECT id FROM users WHERE email='' AND password='' OR 1=1 LIMIT 1
SQL是一种声明性语言,您可以使用它声明对结果的期望。如果您的服务器将如上所述解释我们的输入,则第一个用户id
将被视为正确,只是因为一个等于一。
答案 1 :(得分:1)
实际上,它易受SQL注入
的影响尝试注入时要注意的是我可以关闭我现在所处的语句并添加更多内容。
因此,如果输入username = 123456' --
,则SQL语句将变为SELECT * FROM leerling WHERE leerlingnummer='123456' --' and wachtwoord='unimortant'
- 开始发表评论,所以它只是选择输入的学生编号,忽略密码。
PDO有很好的替代方法可以防止这种情况发生,称为Prepared Statements。您声明了SQL查询,并且仅使用?
或:lable
输入要输入用户信息的位置,然后将用户输入绑定到这些点。该页面在解释它方面做得更好。这样,所有用户数据都清楚地与命令的其余部分分开,并将被视为一个字符串而不是命令。停止SQL注入。
答案 2 :(得分:1)
$sql="SELECT * FROM users WHERE username = '{$_REQUEST['username']}' AND password = '{$_REQUEST['password']}";
以这种格式写查询将避免sql注入。
$sql = 'SELECT * FROM users WHERE username = ? AND password = ?';
$query = $db->prepare($sql);
$query->bindParam(1, $_REQUEST['username']);
$query->bindParam(2, $_REQUEST['password']);
或者将参数传递给mysql_real_escape_string函数,然后传递给查询。
$username=mysql_real_escape_string($_REQUEST['username']);
$password=mysql_real_escape_string($_REQUEST['password']);