谁在抛出(并捕获)这个 MySQL 异常?

Posted

技术标签:

【中文标题】谁在抛出(并捕获)这个 MySQL 异常?【英文标题】:Who is throwing (and catching) this MySQL Exception? 【发布时间】:2011-01-18 12:02:29 【问题描述】:

我将 Python 与 mysql 和 Django 一起使用。我一直看到这个错误,但我无法弄清楚异常是在哪里引发的:

Exception _mysql_exceptions.ProgrammingError: (2014, "Commands out of sync; you can't run this command now") in <bound method Cursor.__del__ of <MySQLdb.cursors.Cursor object at 0x20108150>> ignored

我的代码中有许多“尝试”和“异常”块——如果异常发生在其中一个块中,那么我会看到自己的调试消息。上面的异常显然在某个地方被捕获,因为我的程序在抛出异常时没有中止。

我很困惑,谁能帮帮我?

【问题讨论】:

【参考方案1】:

这是一个 Python 错误。

见:http://eric.lubow.org/2009/python/pythons-mysqldb-2014-error-commands-out-of-sync/

您的 MySQLdb 查询似乎有问题。

【讨论】:

感谢您的链接。我不使用任何显式 MySQL 查询或使用任何游标对象。我所做的所有查询都通过 Django 对象进行。对我来说,一个大问题是无法查看抛出此异常的位置。 恢复:和 php 一样,如果不关闭第一个连接,就无法打开第二个 mysql 连接!【参考方案2】:

我相信如果您在多个线程中使用相同的连接/游标,则可能会发生此错误。 但是,我不认为 Django 的创建者犯了这样的错误,但是如果您自己做某事,则很容易发生。

【讨论】:

我的程序中没有多线程,我的程序也只有一个实例正在运行。当我的程序运行时,我应该是唯一一个访问数据库的人。是否有任何调试技术可以查看抛出异常的位置?我的程序设置为运行大量数据。如果我只测试一小部分数据,一切都很好。但是当我将它设置为在整个集合上运行时,会出现这个 MySQL 异常......现在,我正在运行整个集合并通过管道传输标准输入和标准错误,看看我是否可以更好地了解问题出现了。【参考方案3】:

打印了一堆东西并调试之后,我想出了我认为的问题。我使用的库之一没有关闭连接或光标。但是这个问题只有在我遍历大量数据时才会出现。这个问题也很断断续续,我仍然不知道是谁抛出了“命令不同步”异常。但是现在我们关闭了连接和光标,我再也看不到错误了。

【讨论】:

【参考方案4】:

我确实遇到了那个错误(使用 MySQLdb 和 Django),并发现它被“忽略”的原因是它发生在 __del__ 方法中。 __del__ 中的异常被绝对忽略: object.__del__ datamodel

似乎没有任何方法可以从堆栈的更深处捕获它(至少根据this thread),但您可以编辑 MySQLdb/cursors.py 或 monkey-patch 以获取您自己的__del__在那里捕获异常并将您放入 pdb 提示符或记录完整的回溯。

【讨论】:

您是否能够确定最终导致错误的特定代码?我想知道在 Django 中使用 mysql 是否存在特定问题,一个公共模块,或者特别是我的代码。 根本问题完全是我的错(在线程之间共享数据库连接),并且在关闭连接时发生异常,试图刷新结果集。 Django 在这件事上的唯一责任是,像往常一样,当任何远程意外发生时,它无法调试。 老兄,你是救生员。我收到此错误是因为在创建表之前我有一个 DROP TABLE 语句,但在尝试调试它时我失去了理智,我没有线程通过同一个 conn,什么都没有。【参考方案5】:

对象析构函数 (__del__) 中的异常被忽略,此消息表明了这一点。如果您执行某些 MySQL 命令而不从游标中获取结果(例如“创建过程”或“插入”),则在游标被销毁之前不会注意到异常。 如果您想引发并捕获异常,请在超出范围之前在某处显式调用 cursor.close()

【讨论】:

以上是关于谁在抛出(并捕获)这个 MySQL 异常?的主要内容,如果未能解决你的问题,请参考以下文章

谁在 close 方法中捕获异常?(try-with-resources)

当它被抛出和捕获时,不要在那个异常处停止调试器

spring自己抛出异常,居然不能回滚

开发之统一异常处理

Java中的异常的捕获和抛出是啥意思,有啥区别

在抛出“NSException”(gdb)的实例后调用终止