Python,“命令不同步;现在无法运行此命令”

2024-06-17 09:57:32 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个从Python执行的MySQL存储过程(包装在Django中)。当我试图执行第二条语句时,出现错误“commands out of sync;you can't run this command now”。此时我无法提交事务。这只是我调用过程时的问题。怎么办?

cursor.callproc('my_mysql_procedure', [some_id,]) 
result = cursor.fetchall()
for r in result:
    do something

cursor.execute("select * from some_table")
result = cursor.fetchall()

编辑:我被要求发布MySQL过程。我把它做得非常简单,但我仍然看到同样的问题

delimiter $$
create procedure my_mysql_procedure(p_page_id int)
    begin

        select 1
        from dual; 

    end$$
delimiter ;

Tags: djangofromid过程mymysqlsome语句
3条回答

这不是python问题,而是mysql问题。从perl执行同样的操作,您将得到同样的错误。一般来说,我在运行mysql控制台时会看到这条消息,然后从另一个控制台终止它,然后尝试从终止的控制台运行查询。

有什么东西破坏了你的陈述之间的联系。很可能是你的程序出错了。检查mysql错误日志。

造成这种情况的主要原因是在进行新查询之前没有从光标获取结果。可能有多个结果集。

要停止错误,必须确保每次使用.nextset时都使用结果集。如果它产生多个结果集-你甚至可能需要做其中的一些。

cursor.callproc('my_mysql_procedure', [some_id,]) 
result = cursor.fetchall()
for r in result:
    do something
cursor.nextset()
cursor.execute("select * from some_table")
result = cursor.fetchall()

在我的例子中,我发现这实际上是sql查询中其他问题的一个指示器,这些问题在进行后续查询之前不会被选为python错误。他们产生了多个结果集。

把这个应用到下面的例子中(我看到了同样的错误)

>>> import MySQLdb
>>> conn = MySQLdb.connect(passwd="root", db="test")
>>> cur = conn.cursor()
>>> cur.execute("insert into foo values (1););")
1L
>>> cur.nextset()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/lib/python2.7/dist-packages/MySQLdb/cursors.py", line 107, in nextset
    nr = db.next_result()
_mysql_exceptions.ProgrammingError: (1064, "You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ')' at line 1

这里-因为一个解析错误(一些受信任的输入数据,被代码屏蔽)导致分号,然后是一个新语句-这产生了多个结果集。对于这个语句,它不会产生错误,但是对于下一个试图在游标上运行命令的语句,它会产生错误。

我制作了一个github repo-https://github.com/odmsolutions/mysql_python_out_of_sync_demo-来演示和测试这个。


原始答案: 请查看https://github.com/farcepest/MySQLdb1/issues/28以获取有关如何使用3行代码可靠地重现此内容的详细信息:

再现这一点的最小情况: (假设您有一个空数据库,并且只创建了一个到该数据库的连接,称为conn)

>>> conn.query("Create table foo(bar int(11))")
>>> conn.query("insert into foo values (1););")
>>> conn.query("insert into foo values (2););")
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
_mysql_exceptions.ProgrammingError: (2014, "Commands out of sync; you can't run this command now")

这是生成的错误语法,从错误中我看不出是这个问题。

尝试按照Bukzor的建议检查最后一个查询或过程-并尝试在原始mysql客户机中运行它以查看真正的问题。

感谢JoshuaBoshi的回答,解决了问题。调用过程后,我必须关闭光标并再次打开它,然后才能使用它执行另一条语句:

cursor.close() 

cursor = connection.cursor() 

光标可以在fetchall()之后立即关闭。结果集仍然存在,并且可以循环通过。

相关问题 更多 >