111

我正在尝试执行我的 PHP 代码,该代码通过 mysqli 调用两个 MySQL 查询,并收到错误“命令不同步;您现在无法运行此命令”。

这是我正在使用的代码

<?php
$con = mysqli_connect("localhost", "user", "password", "db");
if (!$con) {
    echo "Can't connect to MySQL Server. Errorcode: %s\n". Mysqli_connect_error();
    exit;
}
$con->query("SET NAMES 'utf8'");
$brand ="o";
$countQuery = "SELECT ARTICLE_NO FROM AUCTIONS WHERE upper(ARTICLE_NAME) LIKE % ? %";
if ($numRecords = $con->prepare($countQuery)) {
    $numRecords->bind_param("s", $brand);
    $numRecords->execute();
    $data = $con->query($countQuery) or die(print_r($con->error));
    $rowcount = $data->num_rows;
    $rows = getRowsByArticleSearch("test", "Auctions", " ");
    $last = ceil($rowcount/$page_rows);
}  else {

print_r($con->error);
}
foreach ($rows as $row) {
    $pk = $row['ARTICLE_NO'];
    echo '<tr>' . "\n";
    echo '<td><a href="#" onclick="updateByPk(\'Layer2\', \'' . $pk . '\')">'.$row['USERNAME'].'</a></td>' . "\n";
    echo '<td><a href="#" onclick="updateByPk(\'Layer2\', \'' . $pk . '\')">'.$row['shortDate'].'</a></td>' . "\n";
    echo '<td><a href="#" onclick="deleterec(\'Layer2\', \'' . $pk . '\')">DELETE RECORD</a></td>' . "\n";
    echo '</tr>' . "\n";
}
function getRowsByArticleSearch($searchString, $table, $max) {
    $con = mysqli_connect("localhost", "user", "password", "db");
    $recordsQuery = "SELECT ARTICLE_NO, USERNAME, ACCESSSTARTS, ARTICLE_NAME, date_format(str_to_date(ACCESSSTARTS, '%d/%m/%Y %k:%i:%s'), '%d %m %Y' ) AS shortDate FROM AUCTIONS WHERE upper(ARTICLE_NAME) LIKE '%?%' ORDER BY str_to_date(ACCESSSTARTS, '%d/%m/%Y %k:%i:%s')" . $max;
    if ($getRecords = $con->prepare($recordsQuery)) {
        $getRecords->bind_param("s", $searchString);
        $getRecords->execute();
        $getRecords->bind_result($ARTICLE_NO, $USERNAME, $ACCESSSTARTS, $ARTICLE_NAME, $shortDate);
        while ($getRecords->fetch()) {
            $result = $con->query($recordsQuery);
            $rows = array();
            while($row = $result->fetch_assoc()) {
                $rows[] = $row;
            }
            return $rows;
        }
    }
}

我已尝试阅读此内容,但我不确定该怎么做。我已阅读有关商店结果和免费结果的信息,但是在使用它们时它们没有任何区别。我不确定这个错误是在哪一点引起的,我想知道为什么会出现这个错误,以及如何解决它。

按照我的调试语句,countQuery 的第一个 if 循环甚至没有被输入,因为我的 sql 语法中的错误 near near '% ? %'。但是,如果我只是选择*而不是尝试基于 LIKE 子句进行限制,我仍然会收到命令不同步错误。

4

22 回答 22

127

您不能同时进行两个查询,因为 mysqli 默认使用无缓冲查询(对于准备好的语句;对于 vanilla 则相反mysql_query)。您可以将第一个获取到数组中并循环遍历,或者告诉 mysqli 缓冲查询(使用$stmt->store_result())。

有关详细信息,请参见此处

于 2009-03-05T13:24:45.990 回答
39

我在我的 C 应用程序中解决了这个问题——我是这样做的:

  1. 引用mysql论坛:

    当您在应用程序中使用分号分隔符终止查询时,会出现此错误。虽然在从命令行或在查询浏览器中执行查询时需要使用分号分隔符来终止查询,但请从应用程序内的查询中删除分隔符。

  2. 在运行我的查询并处理结果 [C API: mysql_store_result()] 之后,我遍历通过多个 SQL 语句执行(例如两个或多个 select 语句(背靠背而不处理结果)发生的任何进一步的潜在未决结果)。

    事实是我的程序没有返回多个结果,但数据库在我执行之前不知道:[C API: mysql_next_result()]。我在一个循环中执行此操作(为了更好地衡量),直到它返回非零。那是当前连接处理程序知道可以执行另一个查询的时候(我缓存我的处理程序以最小化连接开销)。

    这是我使用的循环:

    for(; mysql_next_result(mysql_handler) == 0;) 
      /* do nothing */;
    

我不知道 PHP,但我确信它有类似的东西。

于 2009-11-30T18:08:35.210 回答
18

我今天遇到了同样的问题,但仅在使用存储过程时。这使查询的行为类似于多查询,因此您需要在进行另一个查询之前“使用”其他可用结果。

while($this->mysql->more_results()){
    $this->mysql->next_result();
    $this->mysql->use_result();
}
于 2015-02-20T22:37:58.690 回答
13

我每次在使用 $mysqli->query 之前都会调用这个函数,它也适用于存储过程。

function clearStoredResults(){
    global $mysqli;
    
    do {
         if ($res = $mysqli->store_result()) {
           $res->free();
         }
    } while ($mysqli->more_results() && $mysqli->next_result());        
    
}
于 2016-09-12T15:17:24.390 回答
8

一旦你使用

stmt->execute();

可以关闭它以使用另一个查询。

stmt->close();

这个问题困扰了我好几个小时。希望它会解决你的问题。

于 2019-06-01T14:13:11.313 回答
4

我使用 CodeIgniter。一台服务器好的...这台可能较旧...无论如何使用

$this->db->reconnect();

修复。

于 2012-09-13T00:39:25.787 回答
1

问题在于 MySQL 客户端 C 库,大多数 MySQL API 都是基于该库构建的。问题是 C 库不支持同时执行查询,因此所有基于此构建的 API 也不支持。即使您使用无缓冲查询。这是编写异步 MySQL API 的原因之一。它使用 TCP 直接与 MySQL 服务器通信,并且有线协议支持同时查询。

您的解决方案是修改算法,这样您就不需要同时进行两者,或者将它们更改为使用缓冲查询,这可能是它们存在于 C 库中的原始原因之一(另一个是提供一种游标)。

于 2009-03-06T03:59:25.670 回答
1

要解决此问题,您必须在使用前存储结果数据

$numRecords->execute();

$numRecords->store_result();

就这样

于 2014-10-28T14:53:02.457 回答
1

这是我的问题!

参数绑定是“动态的”,所以我有一个变量来设置数据的参数,以便使用bind_param。所以那个变量是错误的,但不是抛出像“错误的参数数据”这样的错误,而是说“不同步bla bla bla”所以我很困惑......

于 2018-03-06T19:24:59.453 回答
1

另一个原因: store_result() 不能被调用两次。

例如,在以下代码中,将打印错误 5。

<?php

$db = new mysqli("localhost", "something", "something", "something");

$stmt = $db->stmt_init();
if ($stmt->error) printf("Error 1 : %s\n", $stmt->error);

$stmt->prepare("select 1");
if ($stmt->error) printf("Error 2 : %s\n", $stmt->error);

$stmt->execute();
if ($stmt->error) printf("Error 3 : %s\n", $stmt->error);

$stmt->store_result();
if ($stmt->error) printf("Error 4 : %s\n", $stmt->error);

$stmt->store_result();
if ($stmt->error) printf("Error 5 : %s\n", $stmt->error);

(这可能与原始示例代码无关,但可能与寻求此错误答案的人有关。)

于 2019-11-19T00:53:45.930 回答
0

我认为问题在于你在函数中建立了一个新的连接,然后最后没有关闭它。为什么不尝试传入现有连接并重新使用它?

另一种可能性是您正在从 while 循环获取的中间返回。您永远不会完成外部提取。

于 2009-03-05T13:15:13.813 回答
0

检查您是否正确输入了所有参数。如果定义然后传递给函数的参数数量不同,则会引发相同的错误。

于 2015-04-04T16:11:33.727 回答
0

这与原始问题无关,但我有相同的错误消息,这个线程是谷歌的第一个热门话题,我花了一段时间才弄清楚问题是什么,所以它可能对其他人有用:

我没有使用 mysqli,仍在使用 mysql_connect 我有一些简单的查询,但是一个查询导致所有其他查询在同一个连接中失败。

我使用 mysql 5.7 和 php 5.6 我有一个数据类型为“JSON”的表。显然,我的 php 版本无法识别 mysql 的返回值(php 只是不知道如何处理 JSON 格式,因为内置的 mysql 模块太旧了(至少我认为))

现在我将 JSON-Field-Type 更改为 Text(因为现在我不需要本机 mysql JSON 功能)并且一切正常

于 2016-08-16T12:54:36.260 回答
0

清除引用内存,并运行下一个 MYSQL 提取

如果您使用BufferedUnbuffered结果集来获取数据,首先您必须在获取所有数据后简单地从内存中清除获取的数据。因为在清除获取的内存之前,您无法在同一连接上执行另一个 MYSQL 过程。

在脚本的右端添加以下函数,这样就可以解决问题

$numRecords->close(); or $numRecords->free(); // This clears the referencing memory, and will be ready for the next MYSQL fetch

来自 PHP 文档的参考

于 2018-03-05T08:15:39.183 回答
0

我使用 Doctrine DBAL QueryBuilder 遇到了这个错误。

我使用 QueryBuilder 创建了一个使用列子选择的查询,也是使用 QueryBuilder 创建的。子选择仅通过创建$queryBuilder->getSQL()而不执行。创建第二个子选择时发生错误。$queryBuilder->execute()通过使用before using临时执行每个子选择$queryBuilder->getSQL(),一切正常。就好像连接$queryBuilder->connection在执行当前准备的 SQL 之前仍处于创建新 SQL 的无效状态,尽管每个子选择上都有新的 QueryBuilder 实例。

我的解决方案是在没有 QueryBuilder 的情况下编写子选择。

于 2019-03-25T15:41:56.193 回答
0

我正在使用 ODBC,此修复对我有用:ODBC -> 选项卡系统 DSN -> 双击配置我的数据源 -> 详细信息 -> 选项卡游标 ->取消选中[不要缓存只进游标的结果] - > 点击确定

于 2020-04-07T02:08:12.993 回答
0

我经常遇到这个错误,而且总是在我运行我在 phpmyadmin 或 SQL Workbench 中调试的存储过程时(我正在使用 php 连接 mysqli)。

错误是由于调试涉及在代码中的战略点插入 SELECT 语句以告诉我变量的状态等。在这些客户端环境中运行产生多个结果集的存储过程很好,但它会产生“从 php.ini 调用时出现“命令不同步”错误。解决方案始终是注释掉或删除调试选择,因此该过程只有一个结果集。

于 2020-07-16T01:37:34.757 回答
0

multi_query仅供参考,我query在同一代码中混合使用了这个问题:

$connection->multi_query($query);
...
$connection->query($otherQuery);

对于我阅读的内容,未使用的结果未决,因此导致上述错误。

我用一个循环解决了它,消耗了所有的结果multi_query

$connection->multi_query($query);
while ($connection->next_result()); // <--- solves the problem
...
$connection->query($otherQuery);

在我的情况下,所有查询都multi_query插入到了 where 中,所以我对结果本身没有兴趣。

于 2020-10-23T17:59:27.057 回答
-1

我的问题是我使用了第一个准备语句,然后我在同一页面上使用了 mysqli 查询,并收到错误“命令不同步;您现在无法运行此命令”。只有当我使用具有准备语句的代码时,才会出现错误。

我所做的是结束这个问题。它奏效了。

mysqli_stmt_close($stmt);

我的代码

get_category.php (这里使用准备语句)

    <?php


    global $connection;
    $cat_to_delete =    mysqli_real_escape_string($connection, $_GET['get'] );

    $sql = "SELECT category_name FROM categories WHERE category_id = ? ;";


    $stmt = mysqli_stmt_init($connection);

    if (!mysqli_stmt_prepare($stmt, $sql))
        $_SESSION['error'] = "Error at preaparing for deleting query. mysqli_stmt_error($stmt) ." & redirect('../error.php');

    mysqli_stmt_bind_param($stmt, 's', $cat_to_delete);

    if (!mysqli_stmt_execute($stmt))
        $_SESSION['error'] = "ERror at executing delete category ".mysqli_stmt_error($stmt) &
            redirect('../error.php');


    mysqli_stmt_bind_result($stmt, $cat_name);

    if (!mysqli_stmt_fetch($stmt)) {
        mysqli_stmt_error($stmt);
    }



    mysqli_stmt_free_result($stmt);
    mysqli_stmt_close($stmt);

admin_get_category_body.php(这里是 mysqli)

        <?php

        if (isset($_GET['get']) && !empty($_GET['get']) )
        {
            include 'intodb/edit_category.php';
        }


        if (check_method('get') && isset($_GET['delete']) )
        {
            require 'intodb/delete_category.php';
        }


        if (check_method('get') && isset($_GET['get']) )
        {
            require 'intodb/get_category.php';
        }


        ?>

        <!--            start: cat body          -->

        <div     class="columns is-mobile is-centered is-vcentered">
            <div class="column is-half">
                <div   class="section has-background-white-ter box ">


                    <div class="has-text-centered column    " >
                        <h4 class="title is-4">Ctegories</h4>
                    </div>

                    <div class="column " >


                        <?php if (check_method('get') && isset($_GET['get'])) {?>
                        <form action="" method="post">
                            <?php } else {?>
                            <form action="intodb/add_category.php" method="post">
                                <?php } ?>

                                <label class="label" for="admin_add_category_bar">Add Category</label>
                                <div class="field is-grouped">

                                    <p class="control is-expanded">

                                        <?php if (check_method('get') && isset($_GET['get'])) {?>

                                            <input id="admin_add_category_bar" name="admin_add_category_bar_edit" class="input" type="text" placeholder="Add Your Category Here" value="<?php echo $cat_name; ?>">

                                            <?php


                                            ?>
                                        <?php } else {?>
                                            <input id="admin_add_category_bar" name="admin_add_category_bar" class="input" type="text" placeholder="Add Your Category Here">

                                        <?php } ?>
                                    </p>
                                    <p class="control">
                                        <input type="submit" name="admin_add_category_submit" class="button is-info my_fucking_hover_right_arrow" value="Add Category">
                                    </p>
                                </div>
                            </form>


                            <div class="">

                                <!--            start: body for all posts inside admin          -->


                                <table class="table is-bordered">
                                    <thead>
                                    <tr>
                                        <th><p>Category Name</p></th>
                                        <th><p>Edit</p></th>
                                        <th><p>Delete</p></th>
                                    </tr>
                                    </thead>

                                    <?php

                                    global $connection;
                                    $sql = "SELECT * FROM categories ;";

                                    $result = mysqli_query($connection, $sql);
                                    if (!$result) {
                                        echo mysqli_error($connection);
                                    }
                                    while($row = mysqli_fetch_assoc($result))
                                    {
                                        ?>
                                        <tbody>
                                        <tr>
                                            <td><p><?php echo $row['category_name']?></p></td>
                                            <td>
                                                <a href="admin_category.php?get=<?php echo $row['category_id']; ?>" class="button is-info my_fucking_hover_right_arrow" >Edit</a>

                                            </td>

                                            <td>
                                                <a href="admin_category.php?delete=<?php echo $row['category_id']; ?>" class="button is-danger my_fucking_hover_right_arrow" >Delete</a>

                                            </td>
                                        </tr>


                                        </tbody>
                                    <?php }?>
                                </table>

                                <!--           end: body for all posts inside admin             -->




                            </div>

                    </div>
                </div>


            </div>

        </div>
        </div>

我刚刚想到的东西,我也再次通过全局 $connection 添加连接变量;。所以我认为,在使用 mysqli_stmt_close($stmt); 结束准备语句后,基本上会启动一套全新的查询系统;而且我正在通过包含添加这些文件和其他东西

于 2019-05-04T12:57:24.783 回答
-1

这是一个老问题,但是在我的情况下,发布的答案都不起作用,我发现在我的情况下,我在存储过程中的一个表上进行了选择和更新,同一个表有一个更新触发器,该触发器正在被触发并发送程序进入无限循环。一旦发现错误,错误就消失了。

于 2020-06-08T04:25:19.217 回答
-1

此错误的最终解决方案如下:

1)您必须将此代码复制并粘贴到存储过程的下一个查询上方。

do if($result=mysqli_store_result($myconnection)){ mysqli_free_result($result); } while(mysqli_more_results($myconnection) && mysqli_next_result($myconnection));

于 2021-12-21T22:18:23.633 回答
-3

创建两个连接,分别使用

$mysqli = new mysqli("localhost", "Admin", "dilhdk", "SMS");

$conn = new mysqli("localhost", "Admin", "dilhdk", "SMS"); 
于 2019-09-11T17:41:14.063 回答