Dar*_*nke 5 php mysqli prepared-statement
从历史上看,我一直都在使用
mysql_real_escape_string()
Run Code Online (Sandbox Code Playgroud)
对于最终触及数据库的用户派生的所有输入.
现在我已经完全转换为MySQLi并且我正在使用带有绑定参数的准备查询,我是否有效地消除了SQL注入攻击的可能性?
我说我不再需要了
mysql_real_escape_string()?
Run Code Online (Sandbox Code Playgroud)
这是我的理解和我的项目的基础:http: //sourceforge.net/projects/mysqldoneright/files/Base/MysqlDoneRight-0.23.tar.gz/download
这不是我想弄错的事情,虽然现在我已经发布它,它也可能影响其他人.
现在,所有用户提供的输入都将以bind_parms结尾.
准备阶段提供的查询是静态的.
这不是那么简单.您可以使用绑定参数而不是仅将应用程序变量插入到SQL表达式中来代替文字值:
$sql = "SELECT * FROM MyTable WHERE id = ".$_GET["id"]; // not safe
$sql = "SELECT * FROM MyTable WHERE id = ?"; // safe
Run Code Online (Sandbox Code Playgroud)
但是如果除了字面值之外还需要将查询的一部分动态化呢?
$sql = "SELECT * FROM MyTable ORDER BY ".$_GET["sortcolumn"]; // not safe
$sql = "SELECT * FROM MyTable ORDER BY ?"; // doesn't work!
Run Code Online (Sandbox Code Playgroud)
该参数将始终被解释为值,而不是列标识符.您可以使用与之ORDER BY 'score'
不同的查询运行查询ORDER BY score
,并且使用参数将被解释为前者 - 常量字符串'score'
,而不是名为列的值score
.
因此,在很多情况下,您必须使用动态SQL并将应用程序变量插入到查询中以获得所需的结果.在这些情况下,查询参数无法帮助您.您仍然必须保持警惕并采取防御措施以防止SQL注入漏洞.
没有框架或数据访问库可以为您完成此工作.您始终可以构造包含SQL注入漏洞的SQL查询字符串,并在数据访问库看到SQL查询之前执行此操作.那怎么知道什么是故意的,什么是缺陷呢?
以下是实现安全SQL查询的方法:
过滤输入. 跟踪插入SQL查询的任何变量数据.使用输入过滤器去除非法字符.例如,如果您期望一个整数,请确保输入被约束为整数.
逃生输出. 此上下文中的输出可以是您发送到数据库服务器的SQL查询.您知道可以对值使用SQL查询参数,但列名称呢?您需要一个标识符的转义/引用函数,就像旧mysql_real_escape_string()
的字符串值一样.
代码评论. 让某人成为第二双眼睛并查看您的SQL代码,以帮助您找到您忽略使用上述两种技术的地方.