Is there a way to log the total number of queries made in a django view?
Question:
I have non-traditional view that responds to an ajax request. Usually, I use the debug toolbar to get the query count, however, since this particular view is simply returning some json, there’s no page for the Debug Toolbar to display itself.
Is there a way to print out the total queries executed in the view to the console?
From browsing the docs, is found qs.query
. However, that just gives what my base orm lookup will be. I’m really looking for the sum total from everything that happens in my view (for instance, additional queries triggered from traversing foreign keys).
Answers:
You can write a middleware for this purpose:
from django.db import connection
class SqlPrintMiddleware(object):
def process_response(self, request, response):
sqltime = 0 # Variable to store execution time
for query in connection.queries:
sqltime += float(query["time"]) # Add the time that the query took to the total
# len(connection.queries) = total number of queries
print "Page render: " + unicode(sqltime) + "sec for " + unicode(len(connection.queries)) + " queries"
return response
And in your settings.py change:
MIDDLEWARE_CLASSES = (
# ...
'your_app.middleware.SqlPrintMiddleware',
# ...
)
Idea was taken from here
Following is a fast and dirty way of calculating the number of DB calls made during a request-response cycle in Django
Create the following function
from django.db import connection
def calculate_db_response_time():
sqltime = 0.0 # Variable to store execution time
for query in connection.queries:
sqltime += float(query["time"]) # Add the time that the query took to the total
print("Page render: "+ str(sqltime)+ "sec for "+ str(len(connection.queries))+ " queries")
Call the calculate_db_response_time() function just before returning response in your View(s).
PS: Make sure that no other DB calls being made after this function is executed
The other way to make this happen at the Project level is to create the following middleware as suggested by #wolendranh answer.
The following snippet is 3.X python version of the answer provided by #wolendranh.
The following snippet can be created as middleware
from django.db import connection
class SqlPrintMiddleware(object):
def process_response(self, request, response):
sqltime = 0.0 # Variable to store execution time
for query in connection.queries:
sqltime += float(query["time"]) # Add the time that the query took to the total
# len(connection.queries) = total number of queries
print("Page render: "+ str(sqltime)+ "sec for "+ str(len(connection.queries))+ " queries")
return response
And in your settings.py change:
MIDDLEWARE_CLASSES = (
# ...
'your_app.middleware.SqlPrintMiddleware',
# ...
)
For a great debug toolbar to see queries and a lot of things you can use Django Debug Toolbar
The first time after installation, the toolbar not show after some search I found the solution
#settings.py
def show_toolbar(request):
return True and DEBUG
DEBUG_TOOLBAR_CONFIG = {
"SHOW_TOOLBAR_CALLBACK" : show_toolbar,
}
Here is the accepted answer rewritten for Python 3 and Django 4.
Define middleware:
from django.db import connection
class SqlPrintMiddleware:
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
response = self.get_response(request)
sqltime = 0
for query in connection.queries:
sqltime += float(query["time"])
print(f"Page render: {sqltime} sec for {len(connection.queries)} queries")
return response
In settings.py:
MIDDLEWARE = (
# ...
'your_app.middleware.SqlPrintMiddleware',
# ...
)
I have non-traditional view that responds to an ajax request. Usually, I use the debug toolbar to get the query count, however, since this particular view is simply returning some json, there’s no page for the Debug Toolbar to display itself.
Is there a way to print out the total queries executed in the view to the console?
From browsing the docs, is found qs.query
. However, that just gives what my base orm lookup will be. I’m really looking for the sum total from everything that happens in my view (for instance, additional queries triggered from traversing foreign keys).
You can write a middleware for this purpose:
from django.db import connection
class SqlPrintMiddleware(object):
def process_response(self, request, response):
sqltime = 0 # Variable to store execution time
for query in connection.queries:
sqltime += float(query["time"]) # Add the time that the query took to the total
# len(connection.queries) = total number of queries
print "Page render: " + unicode(sqltime) + "sec for " + unicode(len(connection.queries)) + " queries"
return response
And in your settings.py change:
MIDDLEWARE_CLASSES = (
# ...
'your_app.middleware.SqlPrintMiddleware',
# ...
)
Idea was taken from here
Following is a fast and dirty way of calculating the number of DB calls made during a request-response cycle in Django
Create the following function
from django.db import connection
def calculate_db_response_time():
sqltime = 0.0 # Variable to store execution time
for query in connection.queries:
sqltime += float(query["time"]) # Add the time that the query took to the total
print("Page render: "+ str(sqltime)+ "sec for "+ str(len(connection.queries))+ " queries")
Call the calculate_db_response_time() function just before returning response in your View(s).
PS: Make sure that no other DB calls being made after this function is executed
The other way to make this happen at the Project level is to create the following middleware as suggested by #wolendranh answer.
The following snippet is 3.X python version of the answer provided by #wolendranh.
The following snippet can be created as middleware
from django.db import connection
class SqlPrintMiddleware(object):
def process_response(self, request, response):
sqltime = 0.0 # Variable to store execution time
for query in connection.queries:
sqltime += float(query["time"]) # Add the time that the query took to the total
# len(connection.queries) = total number of queries
print("Page render: "+ str(sqltime)+ "sec for "+ str(len(connection.queries))+ " queries")
return response
And in your settings.py change:
MIDDLEWARE_CLASSES = (
# ...
'your_app.middleware.SqlPrintMiddleware',
# ...
)
For a great debug toolbar to see queries and a lot of things you can use Django Debug Toolbar
The first time after installation, the toolbar not show after some search I found the solution
#settings.py
def show_toolbar(request):
return True and DEBUG
DEBUG_TOOLBAR_CONFIG = {
"SHOW_TOOLBAR_CALLBACK" : show_toolbar,
}
Here is the accepted answer rewritten for Python 3 and Django 4.
Define middleware:
from django.db import connection
class SqlPrintMiddleware:
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
response = self.get_response(request)
sqltime = 0
for query in connection.queries:
sqltime += float(query["time"])
print(f"Page render: {sqltime} sec for {len(connection.queries)} queries")
return response
In settings.py:
MIDDLEWARE = (
# ...
'your_app.middleware.SqlPrintMiddleware',
# ...
)