记录所有sql查询


97

如何记录django应用程序执行的所有SQL查询?

我想记录所有内容,包括来自管理站点的SQL。我看到了这个问题一个常见问题解答,但是我仍然不知道该放在哪里

from django.db import connection
connection.queries

将所有内容记录到一个文件?

所以我的问题是-我应该怎么做才能拥有一个记录所有SQL语句的文件(例如all-sql.log)?


Answers:


19

也许看看https://github.com/django-debug-toolbar/django-debug-toolbar

它可以让您查看给定页面生成的所有查询。以及它们发生的位置的堆栈跟踪等。

编辑:将所有SQL查询记录到文件等,然后您将要创建一些中间件。中间件在每个请求上运行。这类事情有几个Django片段:

那些与打印到终端有关,但要使其适应使用python的日志记录库并不难。


175

将以下代码段与LOGGING字段合并settings.py

LOGGING = {
    'version': 1,
    'filters': {
        'require_debug_true': {
            '()': 'django.utils.log.RequireDebugTrue',
        }
    },
    'handlers': {
        'console': {
            'level': 'DEBUG',
            'filters': ['require_debug_true'],
            'class': 'logging.StreamHandler',
        }
    },
    'loggers': {
        'django.db.backends': {
            'level': 'DEBUG',
            'handlers': ['console'],
        }
    }
}

通过@ acardenas89答案进行了调整


3
您可能需要在此handlers部分中添加以下内容,以防无法添加处理程序“控制台”:“控制台”错误: 'console':{ 'level':'DEBUG', 'class':'logging.StreamHandler', 'formatter': 'verbose', 'stream': sys.stderr, },
Don Grem 2014年

1
我还需要'version': 1,LOGGING字典。
丹丹

12
请注意,DEBUG必须为TRUE才能实际记录日志。无论记录设置如何。
Janusz Skonieczny

3
哦,还有一件事在Django的测试运行忽略设置,并覆盖DEBUGFalse,所以在测试你必须@override_settings(DEBUG=True)
雅努什Skonieczny

6
如果您启用了根记录器,但又不知道为什么打印两次,我也会'propagate': False在此'handlers': ['console'],行之后添加。让我有点意识到。
安德烈·尼古拉·彼得

44

在settings.py中添加以下粗体语句


如果调试:
    导入日志
    l = logging.getLogger('django.db.backends')
    l.setLevel(logging.DEBUG)
    l.addHandler(logging.StreamHandler())


记录= {
    '版本':1,
    'disable_existing_loggers':否,
    “过滤器”:{
        'require_debug_false':{
            '()':'django.utils.log.RequireDebugFalse'
        }
    },
    “处理程序”:{
        'mail_admins':{
            'level':'ERROR',
            '过滤器':['require_debug_false'],
            'class':'django.utils.log.AdminEmailHandler'
        },“控制台”:{
            'level':'DEBUG',
            'class':'logging.StreamHandler',
        },
    },
    “记录器”:{
        'django.request':{
            'handlers':['mail_admins'],
            'level':'ERROR',
            '宣传':是的,
        }, 'django.db.backends.sqlite3':{
            'level':'DEBUG',
            'handlers':['console'],
        },
    }
}
  

资源/信贷


9
您不需要if顶部的语句和LOGGING更改。该if语句用于是否要在外壳中添加日志记录以立即将其打开(在settings.py中需要的就是LOGGING更改),并且您可能想要django.db.backends而不是sqlite3特定的记录。
M Somerville

我在运行django 1.9的控制台上看不到任何查询。DEBUG = True
西罗Santilli郝海东冠状病六四事件法轮功

1
@CiroSantilli巴拿马文件六四事件法轮功这是一个非常古老的注释,很可能Django 1.9不支持该解决方案。
cevaris '16

在Django 1.9中,DEBUG运行测试时将设置强制设置为False。一种解决方法是在测试中重新启用它
-Mouscellaneous


7

要在测试期间记录SQL查询,您需要做两件事:

  1. django.db.backends 记录器已启用
  2. @override_settings(DEBUG=True) 装饰。

测试运行程序默认情况下将设置DEBUG = False,而忽略您可能在DJANGO_SETTINGS_MODULE中设置的内容。

最低设置:

# https://docs.djangoproject.com/en/dev/ref/settings/#logging
LOGGING = {
    'version': 1,
    'handlers': {
        'console': {
            'class': 'logging.StreamHandler',
        },
    },
    'loggers': {
        'django.db.backends': {
            'level': 'DEBUG',
        },
    },
    'root': {
        'handlers': ['console'],
    }
}

示例测试用例:

from django.contrib.auth.models import User
from django.test import TestCase, override_settings


class UserTests(TestCase):

    # To log queries in tests you need to manually override DEBUG setting
    # because testing sets DEBUG=False by default

    @override_settings(DEBUG=True)
    def test_create_user(self):
        User.objects.create()

2

您只需要:

@override_settings(DEBUG=True)

如果您已经在中打印了SQL调试语句runserver

将装饰器添加到您的class TestA(TestCase)或中test_function

@override_settings(DEBUG=True)
class TestA(TestCase):
...

    @override_settings(DEBUG=True)
    def test_function(self):
    ...

感谢@Janusz Skonieczny的答案!


0

您需要将其放在中间件软件包中。中间件位于webserver / django核心和所有视图之间。它可以在请求之前进行预处理,并在请求完成之后进行后处理。例如,将查询保存到文件中。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.