哪些标记可以在 PDO 准备好的语句中参数化?
我正在使用 PHP/PDO 中的准备好的语句。基本查询工作正常,将值传递给 WHERE 子句:
$stmt = $db->prepare( 'SELECT title FROM episode WHERE id=:id' );
$stmt->bindParam( ':id', $id, PDO::PARAM_INT );
$id = 5;
$stmt->execute();
但是我遇到了需要传递字段名称变量的情况。这个查询(具有适当的绑定)工作正常:
SELECT :field FROM episode WHERE id=:id
这个查询给出了一个错误:
SELECT title FROM :field WHERE id=:id
这个查询没有给出错误,但不返回任何行:
SELECT title FROM episode WHERE :field=:id
那么,在准备好的语句中应该做什么?我可以“参数化”字段名称、表名称等吗?
I'm playing around with prepared statements in PHP/PDO. The basic queries work fine, passing a value to the WHERE clause:
$stmt = $db->prepare( 'SELECT title FROM episode WHERE id=:id' );
$stmt->bindParam( ':id', $id, PDO::PARAM_INT );
$id = 5;
$stmt->execute();
However I have a situation where I need to pass variables for the field names. This query (with appropriate binding) works fine:
SELECT :field FROM episode WHERE id=:id
This one gives an error:
SELECT title FROM :field WHERE id=:id
This one doesn't give an error, but returns no rows:
SELECT title FROM episode WHERE :field=:id
So, what things should work in prepared statements? Can I 'parameterize' field names, table names and so on?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您无法参数化表名、列名或
IN
子句中的任何内容(感谢 c0r0ner 的 指出IN
子句限制)。请参阅此问题,然后PHP 手册中的此注释。
You cannot parameterize table names, column names, or anything in an
IN
clause (thanks to c0r0ner for pointing out theIN
clause restriction).See this question, and subsequently this comment in the PHP manual.
@ Josh Leitzel
这种想法非常具有限制性(在我看来,这只是懒于实现强大解决方案的借口),特别是对于数据库中表达的动态树结构。
考虑以下示例:
我的项目具有逻辑结构:
公司层次结构以实体的形式表示。每个实体可以在一般情况下被视为层次结构的成员或层次结构的特定级别的成员。层次结构本身在表中定义为单个树分支,如下所示:
实体本身表示为:
为了便于使用,我构建了一个算法来创建树的平面视图。 我的意思:
这将导致生成以下平面表示:
处于部门级别的实体将 Division_id、area_id 和 store_id 设为 NULL,区域 area_id 和 store_id 设为 NULL,等等。
下面的具体示例说明了 与此相关的是,它允许您使用类似于以下的语句查询部门的所有子级:
但是,这假设我知道我正在查询的实体的结构级别。这样做会很好:
我知道弄清楚单个实体的结构级别并不难,但假设我正在循环遍历可能并不全部处于同一级别的实体集合。现在我必须为层次结构的每个级别构建一个单独的查询,但如果我可以参数化字段,我可以执行以下操作:
生成更清晰的代码并且只有一个准备好的语句。
整个示例不使用任何用户输入。
只是需要考虑的事情。
@ Josh Leitzel
That thinking is very restrictive (and is in my opinion just an excuse for being too lazy to implement a robust solution), especially for dynamic tree structures expressed in a database.
Consider the following example:
My project has a logical structure:
A company hierarchy is expressed in terms of entities. Each entity can treated in the general case of being a member of the hierarchy or as a member of a specific level of the hierarchy. The hierarchy itself is defined in a table as a single tree branch as follows:
and the entities themselves are expressed as:
For ease of use I've built an algorithm that creates a flat view of the tree. The following concrete example illustrates what I mean:
This would result in the following flat representation being produced:
Entities that are at the division level would have division_id, area_id and store_id as NULL, An area area_id and store_id as NULL, etc.
The nice thing about this is it lets you query all the children of a division using a statement similar to the follow:
However this assumes that I know the structure level of the entity I'm querying. It would be nice to do:
I know it's not hard to figure out the structure level of a single entity, but assume I'm looping through a collection of entities that may not all be at the same level. As it is now I have to build a separate query for each level of the hierarchy, but if I could parameterize fields I could do the following:
resulting in cleaner code and only one prepared statement.
The entire example uses no user input whatsoever.
Just something to consider.
您也不能参数化
IN
子句中的任何内容。You can't parameterize anything within
IN
clause as well.