PDO 参数化查询的工作方式
Posted
技术标签:
【中文标题】PDO 参数化查询的工作方式【英文标题】:The way PDO parametrized query works 【发布时间】:2011-04-13 05:37:36 【问题描述】:请仔细阅读问题。 “我的代码不起作用!!!”这不是通常的愚蠢行为问题。
当我运行此代码时出现预期错误
try
$sth = $dbh->prepare("SELECT id FROM users WHERE name INN(?,?) ");
$sth->execute(array("I'm","d'Artagnan"));
catch (PDOException $e)
echo $e->getMessage();
我收到此错误消息
您的 SQL 语法有错误...在第 1 行的 'INN('I\'m','d\'Artagnan')' 附近
但多年来我一直认为查询和数据是分开发送到服务器的,并且不会相互干扰。因此我有一些问题(尽管我怀疑有人得到答案......)
-
它从哪里得到如此熟悉的字符串表示 - 引用和转义?是专门报告错误还是实际查询的一部分?
实际效果如何?它是否用数据替换占位符?
有没有办法获取整个查询,而不仅仅是一点点,用于调试目的?
更新
mysqli
会按预期执行:它会抛出错误说 near 'INN(?,?)'
【问题讨论】:
@DrColossos 有答案,@Cassy 有解释。 【参考方案1】:尝试添加
$dbh->setAttribute( PDO::ATTR_EMULATE_PREPARES, false );
;)
【讨论】:
宾果游戏!我正要写另一个更新,正是关于这个主题,指向这个手册页上的第二段php.net/manual/en/ref.pdo-mysql.php,并询问是否有办法测试什么模式处于打开状态。刚刚测试了你的代码,它工作。错误消息中没有转义字符串【参考方案2】:我不确定所有细节,但我会尽力回答。
引用发生在数据库端。数据库转义并清理它接收到的所有值(参见项目符号 2),以便正确解释它。 抛出错误的那一刻,数据库(在本例中为 MySQL)打印出它尝试运行的查询。如果它只是显示准备好的部分,这将不会有太大帮助。
不,它没有。在准备时,查询在服务器端编译。当使用值执行查询时,仅传输值。这与直接在数据库上调用 PREPARE 和 EXECUTE 几乎相同。
这取决于您使用的数据库。例如,MySQL 可以将所有查询记录到日志文件中(检查 my.cnf 设置)。但是你也可以在 PHP 端使用debugDumpParams()。
我希望这有点帮助。
【讨论】:
感谢您的明智回应。我不能把 1 和 2 绑在一起。这是否意味着最后它是相同的引用/转义但只是在服务器端进行的? +1 用于回答实际问题,而不是专注于 IN/INN 的事情。因为第一句话解释了语法错误是故意的 @Col。弹片:对于数据库 1 和 2 是两个不同的命令。第一个“注册”一个查询(如果您愿意,可以比喻为一个函数),第二个将参数传递给它。在这种方法中,数据库确切地知道它可以/必须/应该引用查询的哪一部分。它无法对组合查询执行此操作。 我明白了。准备好后我想它不再是查询,而是成为一组带参数的命令,因此无需转义。 哦,伙计。 mysqli 按预期执行 - 错误消息中的 ??s以上是关于PDO 参数化查询的工作方式的主要内容,如果未能解决你的问题,请参考以下文章