我有一个页面生成一个记录列表,我希望通过多种可能性来过滤或缩小这些记录。因此,我正在考虑向SQL查询添加可能的“AND”语句。除了传递给查询的LIMIT部分的分页之外,用户生成的数据不会进入查询。
我的问题:
在LIMIT之后注释是否开放,因为我没有使用bindParam?
$start_record = $_GET['page'];
$ids = array('pid_b', 'pid_l', 'pid_g' );
$qMarks = str_repeat('?,', count($ids) - 1) . '?';
// THIS MY CONDITION FOR TESTING PURPOSES ONLY
$testVar = 1;
// NOW WE BUILD THE QUERY
$sqlQuery = "SELECT * FROM inventory_tbl ";
$sqlQuery .= "WHERE `consignor_record_id` IN ($qMarks) ';
$sqlQuery .= ($testVar == 1 ? " AND `inventory_status` <> 'active' " : "");
$sqlQuery .= "ORDER BY `created_date` DESC LIMIT $start_record, 50 ;";
$productSearch = $dbh->prepare( $sqlQuery );
答案 0 :(得分:2)
然后是的,它是开放的SQL注入。一个主要的SQL注入问题是通过union加入多个查询。如果我知道inventory_tbl有多少列以及其他类似于users表的名称,我可以发送页面获取值0 UNION ALL SELECT col1,col2 FROM USERS --
,它实际上会从库存表中选择零行并从中选择所有行用户表或类似。或者,如果这不起作用,请发送执行其他代码的限制的子查询。或者甚至是分号来结束select和除了first之外还要执行的任何其他查询。
答案 1 :(得分:1)
来自PDO Wiki
在仿真模式下(默认情况下处于启用状态),PDO替代 占位符与实际数据。和&#34;懒惰&#34;绑定(使用数组) execute()),PDO将每个参数视为字符串。结果, 准备LIMIT?,?查询变为极限&#39; 10&#39;,&#39; 10&#39;这是无效的 导致查询失败的语法。
解决方案是关闭模拟(因为MySQL可以排序所有 占位符正确)。
$start_record = 1;//$_GET['page'];
$ids = array('pid_b', 'pid_l', 'pid_g' );
// THIS MY CONDITION FOR TESTING PURPOSES ONLY
$testVar = 1;
//Set up parameters for lazy binding
$params =$ids;//Fill array with ids
array_push($params,$testVar);
array_push($params,$start_record);
$qMarks = str_repeat('?,', count($ids) - 1) . '?';
// NOW WE BUILD THE QUERY
$sqlQuery = "SELECT * FROM inventory_tbl ";
$sqlQuery .= "WHERE `consignor_record_id` IN ($qMarks) ";
$sqlQuery .= "AND $testVar == ? AND `inventory_status` <> 'active' " ;
$sqlQuery .= "ORDER BY `created_date` DESC LIMIT ?, 50 ;";
//To turn emulation off, one can run this code (or set in a connection options array):
$conn->setAttribute( PDO::ATTR_EMULATE_PREPARES, false );
$productSearch = $dbh->prepare($sqlQuery );
$productSearch->execute($params);
//Remove echos after testing
echo $sqlQuery;
echo "<br>";
var_dump($params);
<强>结果强>
SELECT * FROM inventory_tbl WHERE `consignor_record_id` IN (?,?,?) AND 1 == ? AND `inventory_status` <> 'active' ORDER BY `created_date` DESC LIMIT ?, 50 ;
延迟绑定的参数
array(5) { [0]=> string(5) "pid_b" [1]=> string(5) "pid_l" [2]=> string(5) "pid_g" [3]=> int(1) [4]=> int(1) }
答案 2 :(得分:0)
此查询不能安全注入。您可以通过$ _GET ['page']注入。