【问题标题】:Invalid parameter number: number of bound variables does not match number of tokens'无效的参数号:绑定变量的数量与标记的数量不匹配
【发布时间】:2014-01-14 19:49:48
【问题描述】:

我有一个填充$row["app_id"] 的查询,当我浏览我的div id="reveal" 时,app_id 发生了变化。我要做的是将 app_id 插入 $revealstmt 查询中。我不断收到错误消息。

 Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[HY093]: Invalid     
 parameter number: number of bound variables does not match number of tokens

我的代码如下

    <?php   
    $revealid = $row["app_id"];
    while (isset($revealid)){
            $query3 = "";
            $revealstmt = $conn->prepare("SELECT logs.time_entry AS logs_entry, logs.description AS logs_description, substates.name AS reveal_substates_name FROM logs LEFT OUTER JOIN applications ON logs.fk_app_id = applications.pk_app_id LEFT OUTER JOIN substates ON logs.fk_substate_id = substates.pk_substate_id WHERE logs.fk_app_id = <?php echo $revealid ?> and time_entry >= curdate() - INTERVAL DAYOFWEEK(curdate()) + 14 DAY ORDER BY time_entry DESC;");
            $revealstmt->execute(array('query3' => $query3));
 ?>

 <div id="<?php echo $row["app_name"];?>" class='reveal-modal'>
    <div id="reveal"> 
            <h1><?php echo $row["app_name"]; echo $revealid; ?>
            <br />
            </h1>
            <div class="accordion">
                    <?php while ($revealrow = $revealstmt->fetch()){?>
                            <h3><a href=""><?php echo $revealrow["logs_entry"]?> -|- <? 
 php echo $revealrow["reveal_substates_name"]; ?></a></h3>
                            <div><?php echo $revealrow["logs_description"]; ?></div>
                    <?php  }  ?> <!-- Close Tag for $revealrow -->
    <?php } ?> <!-- Close tag for the while(isset) -->

我尝试过使用 foreach 但不能,因为 $row["app_id"] 不是一个数组,它一次只返回 1 个数字。

希望我已经提供了所有需要的信息,如果没有,我当然会添加我需要的任何信息。再次感谢社区的所有帮助!

【问题讨论】:

  • query3 在您的 SQL 查询中出现在哪里?另外,我认为您的占位符需要以: 开头。
  • &lt;?php echo $revealid ?&gt; 在查询中做了什么?你已经在 PHP 中了,你不能仅仅这样做。请改用串联。
  • 我很可能是错的,因为我显然正在学习。我认为 query3 是从 SQL 查询返回的数组。另外我会检查连接。我没有意识到你可以在 SQL 查询中做到这一点,我认为你必须回到 php。

标签: php mysql


【解决方案1】:

我相信您的查询准备语句有错误的语法。试试这个:

$revealstmt = $conn->prepare("SELECT logs.time_entry AS logs_entry, logs.description AS   logs_description, substates.name AS reveal_substates_name FROM logs LEFT OUTER JOIN applications ON logs.fk_app_id = applications.pk_app_id LEFT OUTER JOIN substates ON logs.fk_substate_id = substates.pk_substate_id WHERE logs.fk_app_id = ".$revealid." and time_entry >= curdate() - INTERVAL DAYOFWEEK(curdate()) + 14 DAY ORDER BY time_entry DESC;");

如果您回显该值,它应该转到标准输出,而不是您正在准备的字符串/查询。

【讨论】:

  • 非常感谢!!我已经为此工作了将近 2 天,但我不知道我只是在那里射击自己的脚。感谢所有贡献了这么多的人!
  • -1,虽然这回答了 OP 问题,但它的安全性存在缺陷,并且很容易使用 sql injection 进行攻击。
  • @FranciscoPresencia 你是绝对正确的!也没有时间指出这一点......
【解决方案2】:

您应该在查询中使用串联。此外,您不希望查询那么长时间。就像您不会在一行中编写所有 PHP 一样,您的 MySQL 也是如此:它是另一种语言。

$revealstmt = $conn->prepare(
  "SELECT logs.time_entry AS logs_entry, " . 
    "logs.description AS logs_description, " .
    "substates.name AS reveal_substates_name " . 
  "FROM logs LEFT OUTER JOIN applications " .
  "ON logs.fk_app_id = applications.pk_app_id " . 
  "LEFT OUTER JOIN substates ON logs.fk_substate_id = substates.pk_substate_id " .
  "WHERE logs.fk_app_id = " . $revealid . " AND " .
  "time_entry >= curdate() - INTERVAL DAYOFWEEK(curdate()) + 14 DAY " .
  "ORDER BY time_entry DESC;");
$revealstmt->execute();

另一个问题是您试图将query3 分配给某些东西。您的查询中没有 ? 占位符,因此,无需在您的 execute() 中添加任何内容。但是,根据您的$revealid 的来源,其他可行的解决方案可能并不安全。您可以通过以下方式确保其安全:

$revealstmt = $conn->prepare(
  "SELECT logs.time_entry AS logs_entry, " . 
    "logs.description AS logs_description, " .
    "substates.name AS reveal_substates_name " . 
  "FROM logs LEFT OUTER JOIN applications " .
  "ON logs.fk_app_id = applications.pk_app_id " . 
  "LEFT OUTER JOIN substates ON logs.fk_substate_id = substates.pk_substate_id " .
  "WHERE logs.fk_app_id = ? AND " .
  "time_entry >= curdate() - INTERVAL DAYOFWEEK(curdate()) + 14 DAY " .
  "ORDER BY time_entry DESC;");
$revealstmt->execute(array($revealid));

【讨论】:

  • 谢谢你,我现在才开始做很多 SQL,我相信你能说出来,但这绝对是我要开始做的事情。通常,当我在 Workbench 中进行查询时,我会像您一样拥有它们,但是当我将它们放入我的代码中时,我会将它们全部放在一行上。再次感谢您的帮助!
【解决方案3】:

$revealstmt-&gt;execute(array('query3' =&gt; $query3)); 这是您的问题,您的查询没有绑定值,但您仍然在 execute statment 上发送绑定数组。

试试这个:

$revealstmt = $conn->prepare("SELECT logs.time_entry AS logs_entry, logs.description AS   logs_description, substates.name AS reveal_substates_name FROM logs LEFT OUTER JOIN applications ON logs.fk_app_id = applications.pk_app_id LEFT OUTER JOIN substates ON logs.fk_substate_id = substates.pk_substate_id WHERE logs.fk_app_id = :query3 and time_entry >= curdate() - INTERVAL DAYOFWEEK(curdate()) + 14 DAY ORDER BY time_entry DESC;");

然后你通过像这样传递绑定值来执行你的查询:

$revealstmt-&gt;execute(array('query3' =&gt; $revealid));

或者:

$revealstmt-&gt;bindValue(':query3', $revealid);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-04-15
    相关资源
    最近更新 更多