1

好吧,我已经在这个问题上待了几个小时,而对于我的一生,我无法弄清楚出了什么问题。代码如下:

$str = "%" . $_POST['str'] . "%";
$offset = (int) $_POST['offset'];

try {
    $stmt = $dbh->prepare("SELECT * FROM Spells WHERE :col LIKE :str ORDER BY :sort LIMIT 10 OFFSET :offset");
    $stmt->bindParam(":col",$_POST['col']);
    $stmt->bindParam(":str",$str);
    $stmt->bindParam(":offset",$offset, PDO::PARAM_INT);
    $stmt->bindParam(":sort",$_POST['sort']);

    $stmt->execute();
}
catch (PDOException $e) {
    echo "MySQL error: " . $e->getMessage() . "<br/>";
    die();
}

与数据库的连接工作正常,没有发生错误。如果我在%搜索字段中输入(将%%%在查询中输出),结果将按预期返回。

我在 phpMyAdmin 中尝试了相同的查询,它工作正常。我一直在从不推荐使用的mysql_*函数中更新此脚本,这些函数以前运行良好。

先前已弃用的查询示例:

$sql = "SELECT * FROM Spells WHERE " . $col . " LIKE '%" . $str . "%' ORDER BY " . $sort . " LIMIT 10 OFFSET " . $offset;

正如我可能已经说过的,我也一直在这个网站上搜索,试图找到一个解决方案;没有任何效果,甚至 MySQL 的CONCAT('%',:str,'%').

我正在测试的服务器正在运行 php 版本 5.3.17。

如果我没有说清楚,我的问题是我在这里做错了什么?对于那些想知道的人(我以为我放了这个,但显然我没有放),没有错误消息。

4

1 回答 1

2

问题是您不能使用参数代替标识符。这意味着您不能参数化列名或表名。

您的查询在执行时的基本外观是

SELECT * FROM Spells WHERE 'some_column_name' LIKE '%something%'...

我会建立一个搜索和排序列名的白名单,并使用它们来构建您的查询。这是一个非常简单的例子

$search = array('col1', 'col2', 'col3');
$defaultSearch = 'col1';

$sort = array('col1', 'col2');
$defaultSort = 'col1';

$col = in_array($_POST['col'], $search) ? $_POST['col'] : $defaultSearch;
$sort = in_array($_POST['sort'], $sort) ? $_POST['sort'] : $defaultSort;

$sql = sprintf('SELECT * FROM Spell WHERE %s LIKE :str ORDER BY %s LIMIT 10 OFFSET :offset',
    $col, $sort);

$stmt = $dbh->prepare($sql);
// bind :str and :offset, and so on
于 2012-10-17T01:58:58.453 回答