在 Django shell 会话期间获取 SQL 查询计数

Posted

技术标签:

【中文标题】在 Django shell 会话期间获取 SQL 查询计数【英文标题】:Get SQL query count during a Django shell session 【发布时间】:2013-11-02 13:58:37 【问题描述】:

有没有办法在 Django shell 会话期间打印 Django ORM 执行的原始 SQL 查询的数量?

此类信息已由 Django 调试工具栏提供(例如,5 QUERIES in 5.83MS,但如何从 shell 中获取它并不明显。

【问题讨论】:

【参考方案1】:

你可以使用connection.queries:

>>> from django.conf import settings
>>> settings.DEBUG = True
>>> from django.db import connection
>>> Model.objects.count()
>>> print(len(connection.queries))
1

【讨论】:

不幸的是,这似乎不适用于 Django 1.5,查询计数保持在 0 用 Django 1.11 试过这个方法,效果很好! 我的首选之一。对此也很有用:django.db.reset_queries 重置该计数。 注意,这在 9000 处停止计数。请参阅 BaseDatabaseWrapper.queries_limit 这对我不起作用,即使在 Django 1.11 中也是如此。我不得不使用 Tim Richardson 的答案来获得与实际查询的联系。【参考方案2】:

这是对已接受答案的轻微改进。在某些应用程序中创建一个名为 extra_imports.py 的 python 文件(例如some_app

extra_imports.py

from django.conf import settings
settings.DEBUG = True
from django.db import connection, reset_queries


def num_queries(reset=True):
    print(len(connection.queries))
    if reset:
        reset_queries()

现在,如果您正在使用 django_extension 中的 shell_plus(如果您不使用它,请检查一下),将以下行添加到 settings.py

SHELL_PLUS_PRE_IMPORTS = [('some_app.extra_imports', '*')]

如果您使用的是 django shell,请在 shell 中运行它

exec(open('some_app/extra_imports.py').read()) # python3
execfile('some_app/extra_imports.py').read()) # pyhton2

或者你可以将extra_import.py的内容粘贴到shell中

现在,

In [1]: User.objects.all()
In [2]: num_queries()
1

In [3]: User.objects.filter(company=Company.objects.first()).all()
In [4]: num_queries()
2

【讨论】:

【参考方案3】:

如果您有数据库路由和多个连接,则计算您的数据库命中会有点棘手,因为connection.queries 据我所知,仅考虑默认连接。

要包括所有连接:

from django.db import connections,connection,reset_queries
from django.conf import settings
settings.DEBUG = True
...
def query_count_all()->int:
    query_total = 0
    for c in connections.all():
        query_total += len(c.queries)
    return query_total

或更简洁:

def query_count_all()->int:
   return sum(len(c.queries) for c in connections.all())

reset_queries() 已经处理了多个连接

【讨论】:

以上是关于在 Django shell 会话期间获取 SQL 查询计数的主要内容,如果未能解决你的问题,请参考以下文章

SQL Server Alwayson可用性副本会话期间的可能故障

如何在 python 中启用 Django shell 中的历史记录

如何在 django 中设置和获取会话变量?

如何在同一子域上获取不同的 Django 应用程序以共享会话 cookie?

在 Visual Studio 调试会话期间查找当前目录?

从 django 表单获取会话值