pdo通过预处理语句防止sql注入
本文会通过一个简单的登录验证来演示通过预处理语句防注入。
数据库:test;
创建表:
- CREATE TABLE USER(
- id INT UNSIGNED AUTO_INCREMENT KEY,
- username VARCHAR(20) NOT NULL,
- password CHAR(32) NOT NULL,
- email CHAR(32) NOT NULL
- );
向表中插入一条数据:
- INSERT INTO user(username,password,email) VALUES('baby','baby','444@qq.com');
登入界面:
- <!DOCTYPE html>
- <html lang="en">
- <head>
- <meta charset="UTF-8">
- <title>login</title>
- </head>
- <body>
- <form action="check.php" method="post" accept-charset="utf-8">
- 用户名 <input type="text" name="username"><br>
- 密 码 <input type="password" name="psw"><br>
- <input type="submit"value="提交">
- </form>
- </body>
- </html>
1.首先先正常编写check.PHP页面,不做任何处理。
- <?php
- header('content-type:text/html;charset=utf-8');
- $username=$_POST['username'];
- $psw=$_POST['psw'];
- try {
- $pdo=new PDO('mysql:host=localhost;dbname=test','root','root');
- $sql="select * from user where username='{$username}' and password='{$psw}'";
- $stmt=$pdo->query($sql);
- //返回结果集中的行数
- echo $stmt->rowCount();
- } catch (Exception $e) {
- echo $e->getMessage();
- }
- ?>
输入正确的用户名:baby 密码:baby 结果:1 (因为查询到一条记录 通过echo rowCount()输出)
输入错误的用户名或密码 结果:0
输入注入语句 用户名:'or 1=1 # 密码:随便写 结果:1
2.更换为预处理语句(占位符)
- <?php
- header('content-type:text/html;charset=utf-8');
- $username=$_POST['username'];
- $psw=$_POST['psw'];
- try {
- $pdo=new PDO('mysql:host=localhost;dbname=test','root','root');
- $sql="select * from user where username=:username and password=:psw";
- $stmt=$pdo->prepare($sql);
- $stmt->execute(array(":username"=>$username,":psw"=>$psw));
- echo $stmt->rowCount();
- } catch (Exception $e) {
- echo $e->getMessage();
- }
- ?>
或
- <?php
- header('content-type:text/html;charset=utf-8');
- $username=$_POST['username'];
- $psw=$_POST['psw'];
- try {
- $pdo=new PDO('mysql:host=localhost;dbname=test','root','root');
- $sql="select * from user where username=? and password=?";
- $stmt=$pdo->prepare($sql);
- $stmt->execute(array($username,$psw));
- echo $stmt->rowCount();
- } catch (Exception $e) {
- echo $e->getMessage();
- }
- ?>
输入注入语句 用户名:'or 1=1 # 密码:随便写 结果:0 说明已经无法注入。

浙公网安备 33010602011771号