PostgreSQL + PHP:“select * from tab where col in(?)”

时间:2011-01-03 22:34:07

标签: php postgresql binding

以下简短测试脚本

<?php

define('DBHOST', '/tmp');
define('DBNAME', 'XXX');
define('DBUSER', 'XXX');
define('DBPASS', 'XXX');

$ids = array('OK251562715876', 'OK178469380239');

try {
        $db = new PDO('pgsql:host=' . DBHOST . '; dbname=' . DBNAME, DBUSER, DBPASS, $options);
        $db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

        $sth = $db->prepare('select * from pref_money where id in ( ? )');
        $sth->execute($ids);
        while ($row = $sth->fetch(PDO::FETCH_ASSOC))
                print_r($row);

} catch (Exception $e) {
        exit('Database problem: ' . $e->getMessage());
}
?>

因错误而失败:

Database problem: SQLSTATE[42P18]: 
Indeterminate datatype: 7 
ERROR:  could not determine data type of parameter $2

如果我删除了数组的第二个元素,那么它可以正常工作。

是否有可能使用多个元素对数组进行绑定?

我知道我可以使用join()等编写完整的SQL语句字符串并省略问号,但是我需要额外的努力来防止在我的Web脚本中注入SQL ...

在CentOS 5.5下使用PostgreSQL 8.4.6和PHP 5.1.6

3 个答案:

答案 0 :(得分:2)

PDOStatement::execute()期望单个参数是一个参数数组。该数组的每个元素都被视为查询参数。所以现在PDO“认为”你传递两个参数,而你的查询只包含一个参数。

解决方案:传递一个只包含一个元素(参数)的数组,这是一个数组:...->execute(array($ids));

答案 1 :(得分:1)

使用正确数量的问号构建查询 - 以匹配数组的长度 - 然后将数组的内容作为值传递给execute

答案 2 :(得分:1)

如果绑定参数以这种方式工作会很方便,但唉,他们没有。你必须做类似的事情:

$sth = $db->prepare('select * from pref_money where id in (?, ?)');
$sth->execute($ids[0], $ids[1]);

丑陋,可能不是你想要的,但是你可以编写一些代码来使它更友好(例如,自动输入正确数量的问号)。