我应该如何在mysql_query函数中编写PHP $ _POST变量?

时间:2010-01-20 22:07:53

标签: php sql mysql post sql-injection

在访问我的数据库时,我让用户填写表单,并在目标页面中,在生成的MySQL查询中使用发布的值。

$query = mysql_query("SELECT pass FROM database WHERE user='$_POST[user]'");

然而,由于某种原因,MySQL不喜欢我在命令中使用$ _POST变量,它只在我定义(例如)$user = $_POST['user'];时才有效,然后直接将$ user放入SQL命令。

另一方面,我可以在不需要特定列名的INSERT语句中使用$ _POST值:

$query = mysql_query("INSERT INTO database VALUES ('foo', 'bar', '$_POST[user]'");

如果我尝试定义属性的INSERT语句(例如user='foo'),则会出现同样的问题。

我在SQL查询中做错了什么导致命令在运行时出错,但是使用格式化INSERT命令的特定方法?

希望,这不是“运气不好,看起来你必须分配所有发布的价值”。嘿。

5 个答案:

答案 0 :(得分:9)

首先, watch out for SQL Injections

现在,要回答你的问题,请尝试这样做:

$query = mysql_query("SELECT `pass` FROM `database` WHERE `user` LIKE '" . mysql_escape_string($_POST['user']) . "';");

你做错了几件事:

  • 使用=运算符代替LIKE运算符
  • 未使用'
  • 将值括在SQL查询中
  • 未将$_POST数组中的用户索引与'
  • 括起来

PS:您应该使用mysql_real_escape_string()代替mysql_escape_string()

答案 1 :(得分:3)

您只是将一个变量插入一个字符串中,因此将它放入哪个命令无关紧要。

有几点需要指出。

一,您可能希望将{}格式用于数组变量。您不要在此格式的arrray键名称周围使用引号。

$query = mysql_query("SELECT pass FROM database WHERE user='{$_POST[user]}'")

二,你永远不想做那样的查询,因为你对sql注入漏洞持开放态度。考虑一下,如果$ _POST ['user']是“cow”; drop table database; - “?

您必须先在POST输入上运行mysql_real_escape_string,然后再将其放入查询中,或者使用带有预准备语句的PHP PDO结账。

格式化字符串的一种方法是使用sprintf。

$query=mysql_query(sprintf("SELECT pass FROM database WHERE user='%s'",mysql_real_escape_string($_POST['user'])));

答案 2 :(得分:2)

  1. 使用PDO - 它提供了更好的API来与数据库进行通信。
  2. 如果您使用mysql_*()功能,请始终记住过滤mysql_real_escape_string())来自不受信任来源的任何数据(如用户)
  3. 更加关注代码的外观。只需比较以下列表:

    $query = mysql_query("INSERT INTO database VALUES ('foo', 'bar', " . mysql_real_escape_string($_POST['user']) . ", " . mysql_real_escape_string($_POST['user']) . ", " . mysql_real_escape_string($_POST['user']) . ", " . mysql_real_escape_string($_POST['user']) . ")");
    
    $query = sprinf('INSERT INTO database VALUES ("foo", "bar", "%s", "%s", "%s")',
    mysql_real_escape(...), ...);
    

    我是否必须解释哪一个更适合阅读,修改或理解?

答案 3 :(得分:1)

为什么不检查一下mysql_error()对它有什么看法?如果您的查询无效,mysql_error()将返回一个很好的文本块,告诉您到底出了什么问题。

对于不喜欢POST var的MySQL,如果你直接插入某些运行,而不是其他运行,那么你应该确保你为每个测试使用一致的数据和设置。如果使用GET完成某些测试,那么您的POST变量将为空。如果您为每个测试使用不同的用户名,那么请查看失败的用户名是否一致。

如上所述,请阅读有关SQL注入以及您的查询如何被恶意用户破坏的信息。

答案 4 :(得分:0)

尝试

$query = mysql_query("SELECT pass FROM database WHERE user=" . mysql_real_escape_string($_POST['user']));

$query = mysql_query("INSERT INTO database VALUES ('foo', 'bar', " . mysql_real_escape_string($_POST['user']) . ")");

清理通过$ _GET或$ _POST

收到的任何内容总是一个好主意