小熊奶糖(BearCandy)
小熊奶糖(BearCandy)
发布于 2024-03-26 / 32 阅读
0
0

php使用real_escape_string转义以及stmt预处理,以及php8新增execute_query预处理

在PHP中,为了防止SQL注入攻击,有两种主要的方法来确保用户输入的安全性,当向MySQL数据库插入数据时:

  1. mysqli_real_escape_string()
    mysqli_real_escape_string() 是MySQLi扩展提供的一个函数,它会对字符串中的特殊字符进行转义,特别是那些可能导致SQL注入的字符,如单引号 (')、双引号 (")、反斜线 (\) 和NULL字节。使用方法如下:

    $conn = mysqli_connect("localhost", "username", "password", "database");
    $unescaped_string = $_POST['user_input'];
    $escaped_string = mysqli_real_escape_string($conn, $unescaped_string);
    // 使用转义后的字符串构建SQL查询
    $sql = "INSERT INTO table (column) VALUES ('$escaped_string')";
    mysqli_query($conn, $sql);
    

    注意,这个函数的效果依赖于当前数据库连接的字符集设置,所以在使用前应当确保已经正确设置了连接的字符集,否则可能会有潜在的安全风险。

  2. 预处理语句(Prepared Statements)
    预处理语句是一种更安全的方式来执行动态SQL,它会在服务器端独立编译SQL模板,并将用户输入作为参数传递,从而彻底杜绝SQL注入。在PHP中,你可以使用MySQLi或PDO扩展来实现预处理语句。

    使用MySQLi

    $stmt = mysqli_prepare($conn, "INSERT INTO table (column) VALUES (?)");
    mysqli_stmt_bind_param($stmt, "s", $unescaped_string);
    mysqli_stmt_execute($stmt);
    

    或者在PHP 8中,如果MySQLi扩展引入了新的接口(实际上PHP 8并没有增加 execute_query这样的新方法),假设存在类似简化的方法,可能是这样的:

    // 假设PHP 8中存在某种简化形式,但实际上并不真实存在
    $stmt = mysqli_prepare_and_execute($conn, "INSERT INTO table (column) VALUES (?)", [$unescaped_string]);
    

    **其中的?为占位符
    通过告诉数据库参数的数据类型,可以降低 SQL 注入的风险。参数有
    以下四种类型:
    •i-integer(整型)
    •d-double(双精度浮点型)
    ※s-string(字符串)
    •b-BLOB(binary large object:二进制大对象)
    每个参数都需要指定类型。

    //预处理
    $sql = "INSERT INTO user (username, password, phone)VALUES (?,?,?)";
    $stmt = $conn->prepare($sql);
    $stmt->bind_param("sss",$username,$password, $phone);
    //执行
    $stmt->execute();
    //获取结果
    if ($stmt->affected_rows >e) {
    echo“插入成功“;
    } else {
    echo“插入失败”;
    

    使用PDO**:

    $pdo = new PDO("mysql:host=localhost;dbname=database;charset=utf8", "username", "password");
    $stmt = $pdo->prepare("INSERT INTO table (column) VALUES (:value)");
    $stmt->bindParam(':value', $unescaped_string);
    $stmt->execute();
    

    预处理的优势在于它将SQL结构与数据值分离,确保了即使用户输入包含恶意的SQL代码,也不会被执行,而是当作普通文本对待。

    php8新方法

    $name=“这是一个‘送命题'“;
    //mysqli_execute_query
    $sql = "INSERT INTO user (username, password, phone)
    VALUES (?,?,?)1';
    conn->execute_query(conn−>executequery(sql,[$name,'123456','13888888888']);
    

无论是PHP 7还是PHP 8,预处理语句的使用方式都是推荐的最佳实践,因为它能提供更高的安全性并可提高性能(因为对于相同的查询结构,数据库只需解析一次)。


评论