为了账号安全,请及时绑定邮箱和手机立即绑定

如何在php中创建安全的MySQL准备语句?

如何在php中创建安全的MySQL准备语句?

ABOUTYOU 2019-06-21 15:54:18
如何在php中创建安全的MySQL准备语句?我对用php在MySQL中使用准备好的语句很陌生。我需要一些帮助来创建一个准备好的语句来检索列。我需要从不同的专栏中得到信息。当前,对于测试文件,我使用完全不安全SQL语句:$qry = "SELECT * FROM mytable where userid='{$_GET['userid']}' AND category='{$_GET['category']}'ORDER BY id DESC"$result = mysql_query($qry)  or die(mysql_error());有人能帮我创建一个安全MySQL语句使用从url参数(如上面)准备的输入?额外好处:准备好的语句也会提高速度。如果我只在一页上使用准备好的报表三、四次,它会提高总体速度吗?
查看完整描述

3 回答

?
海绵宝宝撒

TA贡献1809条经验 获得超8个赞

下面是一个使用mysqli的示例(对象语法-如果您愿意的话,可以很容易地转换为函数语法):

$db = new mysqli("host","user","pw","database");$stmt = $db->prepare("SELECT * FROM mytable where userid=? AND category=? ORDER BY id DESC");
$stmt->bind_param('ii', intval($_GET['userid']), intval($_GET['category']));$stmt->execute();$stmt->store_result();
$stmt->bind_result($column1, $column2, $column3);while($stmt->fetch()){
    echo "col1=$column1, col2=$column2, col3=$column3 \n";}$stmt->close();

此外,如果您希望找到一种简单的方法来获取关联数组(用于select*),而不必指定要绑定到哪些变量,那么这里有一个方便的函数:

function stmt_bind_assoc (&$stmt, &$out) {
    $data = mysqli_stmt_result_metadata($stmt);
    $fields = array();
    $out = array();

    $fields[0] = $stmt;
    $count = 1;

    while($field = mysqli_fetch_field($data)) {
        $fields[$count] = &$out[$field->name];
        $count++;
    }
    call_user_func_array(mysqli_stmt_bind_result, $fields);}

要使用它,只需调用它,而不是调用BIND_RE结局:

$stmt->store_result();$resultrow = array();stmt_bind_assoc($stmt, $resultrow);while($stmt->fetch()){
    print_r($resultrow);}


查看完整回答
反对 回复 2019-06-21
?
qq_花开花谢_0

TA贡献1835条经验 获得超7个赞

我同意其他几个答案:

  • PHP

    ext/mysql

    不支持参数化SQL语句。
  • 在防范SQL注入问题时,查询参数被认为更可靠。
  • mysql_real_escape_string()

    如果您正确地使用它,也可能是有效的,但它的代码更冗长。
  • 在某些版本中,国际字符集存在字符不能正确转义的情况,从而留下微妙的漏洞。使用查询参数可以避免这些情况。

您还应该注意,即使使用查询参数,仍然必须对SQL注入保持谨慎,因为参数仅取代SQL查询中的文字值。如果动态生成SQL查询,并将PHP变量用于表名、列名或SQL语法的任何其他部分,则查询参数和mysql_real_escape_string()帮我处理这个案子。例如:

$query = "SELECT * FROM $the_table ORDER BY $some_column";

关于业绩:

  • 当您使用不同的参数值多次执行准备好的查询时,性能就会有好处。您避免了解析和准备查询的开销。但是,您需要在同一个PHP请求中多次执行相同的SQL查询吗?
  • 即使您可以利用这一性能优势,与您为解决性能问题所能做的许多其他事情相比,它通常也只是轻微的改进,比如有效地使用操作码缓存或数据缓存。
  • 甚至有些情况下,准备好的查询害处表演。例如,在下面的情况下,优化器不能假设它可以使用索引进行搜索,因为它必须假定参数值强权从通配符开始:

    SELECT * FROM mytable WHERE textfield LIKE ?


查看完整回答
反对 回复 2019-06-21
  • 3 回答
  • 0 关注
  • 486 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信