【问题标题】:Make this query safe? [duplicate]让这个查询安全吗? [复制]
【发布时间】:2010-02-25 18:36:38
【问题描述】:

可能重复:
Best way to stop SQL Injection in PHP

我已经看到一些使用称为 PDO 的示例来使查询免受 sql 感染,或者其他使用 real_escape 的示例,但它们似乎都不完整或假设一些知识。所以我问,采用这个简单的更新查询并使其免受 sql-injection 的影响。

function updateUserName($id,$first,$last)
{
    $qry = 'UPDATE user SET first = "'.$first.'", last = "'.$last.'" WHERE id = '.$id;
    mysql_query($qry) or die(mysql_error());
}

【问题讨论】:

标签: php security sql-injection


【解决方案1】:

基本上,你必须:

在你的具体情况下,会给出这样的结果:

$qry = 'UPDATE user SET first = "'
    . mysql_real_escape_string($first)
    . ' ", last = "'
    . mysql_real_escape_string($last)
    . '" WHERE id = '
    . intval($id);

当然,这是考虑到lastfirst 是varchar,而id 是整数。


作为旁注:当发生 SQL 错误(无论你能解决什么类型的错误也是如此),你不应该显示技术错误消息,而只是让脚本死掉。

您的用户不会理解该技术错误消息——他们不知道如何处理它,这不是他们的问题。

相反,您应该将技术错误消息记录在(例如,记录到文件中),以供您自己使用;并向用户显示一个漂亮的“糟糕,发生错误”页面。

【讨论】:

    【解决方案2】:

    这是更好的查询:

    $qry = 'UPDATE user SET first = "'.mysql_real_escape_string($first).'", last = "'.mysql_real_escape_string($last).'" WHERE id = '.intval($id);
    

    mysql_real_escape_string 用于字符串,将intval 用于查询中的数字,以使它们更安全。

    【讨论】:

      【解决方案3】:

      mysql_real_escape_string + sprintf

      $qry = sprintf('UPDATE user SET first = '%s', last = '%s' WHERE id = %d', mysql_real_escape_string($first), mysql_real_escape_string($last), $id);
      

      我喜欢这样。

      【讨论】:

      • +1 for sprintf 这将使您不必在非字符串变量上进行输入。
      【解决方案4】:

      您可以将所有变量包装在mysql_real_escape_string() 中。但是,如果 PDO(PHP 数据对象)在您的环境中可用,它是一个更好的解决方案。你可以找到这些文档here

      PDO 将使您的代码更加面向对象,并为您自动执行其中一些任务。可以在文档here 的更深处找到一些好的 PDO 准备语句示例代码。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2012-10-14
        • 2015-12-24
        • 1970-01-01
        • 2013-04-09
        相关资源
        最近更新 更多