PDO IST不是在目标系统我工作的支持,虽然我寻求防止使用PHP的5.1.x在Postgres的-DB 8.2或以上版本 SQL注入的解决方案。目前有没有切换到PDO的机会。pg_prepare()预处理语句(不是PDO)是否阻止SQL注入?
我目前的解决方案是pg_prepare准备声明:
// Trying to prevent SQL-Injection
$query = 'SELECT * FROM user WHERE login=$1 and password=md5($2)';
$result = pg_prepare($dbconn, "", $query);
$result = pg_execute($dbconn, "", array($_POST["user"], $_POST["password"]));
if (pg_num_rows($result) < 1) {
die ("failure");
}
但pg_prepare的文档缺少有关的重要信息:
它讲述了 “以后使用”
pg_prepare()创建一个准备好的语句,以便以后执行时使用 pg_execute()或pg_send_execute()。[...]
它讲述了 “命名的/匿名发言”
功能从 查询字符串创建一个名为stmtname一份准备好的声明,它必须包含一个SQL命令。 stmtname可以是 “”创建一个无名语句,在这种情况下任何预先存在的 无名语句被自动替换; [...]
它讲述了“类型转换”
用于pg_prepare()的准备语句也可以由执行SQL PREPARE语句的 创建。 (但pg_prepare()更灵活 ,因为它不需要预先指定参数类型。)另外, 虽然没有用于删除预准备语句的PHP函数,但可以使用SQL DEALLOCATE语句来实现此目的。
,但它并没有告诉,如果此实现准备好的发言的是SQL注入安全
*几乎所有的评论此安全问题是指PDO的解决方案,其中在文档中发现该驱动程序防止SQL注入。但是,如果一个简单的解决方案可能是pg_prepare,那么我现在会使用pg_prepare。*
感谢您提供可能是最佳实践解决方案的重要信息。
编辑(标记为解决方案后): 非常感人的答案!
- 我将Frank Heikens的解决方案标记为最佳答案,因为它解释了SQL注入中的一个重要问题。程序员可以使用准备好的statemtents,但SQL注入缺乏可能仍然是错误的!
- 除了Frank Heikens的回答,hoppa显示使用pg_prepare/pg_query_params防止SQL注入。不过谢谢。
- 现在将使用与
pg_query_params
(感谢米伦A.拉德夫) - 而
pg_escape_string()
作为替代优化的代码,当涉及到它(感谢halfer)
所有的答案都很有帮助:)
// Trying to prevent SQL-Injection (**updated**)
$sql_query = 'SELECT * FROM user WHERE login=$1 and password=md5($2);';
$result = pg_query_params($dbconn_login, $sql_query, array($_POST["user"], $_POST["password"]));
if (pg_num_rows($result) < 1) {
die('failure');
}
我应该这样认为,但您可以随时尝试查看':)'。注入您自己的'DROP TABLE'语句代替其中一个参数值,并查看是否可以让它删除一个虚拟表。 – halfer 2012-08-10 08:12:37