#5236 closed (wontfix)
Provide stack trace information in sql debug entries
| Reported by: | Owned by: | Philippe Raoult | |
|---|---|---|---|
| Component: | Database layer (models, ORM) | Version: | dev |
| Severity: | Keywords: | feature debug | |
| Cc: | Triage Stage: | Ready for checkin | |
| Has patch: | yes | Needs documentation: | no |
| Needs tests: | no | Patch needs improvement: | no |
| Easy pickings: | no | UI/UX: | no |
Description
Hi,
when profiling django views I often use the list of stored SQL queries to review. What I am missing there is where each of the SQL statements comes from. So I added a stack frame text to each of them.
I have not measured the performance impact, but since it only affects installations with DEBUG=True, I consider the tradeoff acceptable.
The patch also simplifies the debug entry by splitting off the storing to a separate method save_entry().
Attachments (2)
Change History (9)
by , 18 years ago
| Attachment: | django_sql_debug_stack.patch added |
|---|
comment:1 by , 18 years ago
| Has patch: | set |
|---|---|
| Triage Stage: | Unreviewed → Design decision needed |
comment:2 by , 18 years ago
| Keywords: | feature debug added |
|---|
comment:3 by , 18 years ago
| Owner: | changed from to |
|---|
by , 18 years ago
comment:4 by , 18 years ago
| Status: | new → assigned |
|---|
comment:5 by , 18 years ago
| Triage Stage: | Design decision needed → Ready for checkin |
|---|
comment:6 by , 18 years ago
| Resolution: | → wontfix |
|---|---|
| Status: | assigned → closed |
Thanks for taking the time to make the patch, but no thanks. Running with DEBUG=True is useful in a lot of situations and we don't need this type of overhead all the time there.
If you want to do this, you can replace the CursorDebugWrapper.execute with your own function in, say, settings.py, so no changes to core are necessary (the advantage of functions as first class objects).
comment:7 by , 16 years ago
Just in case anybody is still looking for this, create a new app and throw this into the _ _init_ _.py:
from django.conf import settings
DEBUG_SQL_STACK = getattr(settings, 'DEBUG_SQL_STACK', False)
if DEBUG_SQL_STACK:
from time import time
import traceback
import django.db.backends.util
class TracingCursorDebugWrapper(django.db.backends.util.CursorDebugWrapper):
def trace_entry (self, sql, start):
stop = time()
entry = {
'sql': sql,
'time': "%.3f" % (stop - start),
'stack': traceback.format_stack()[:-2],
}
self.db.queries.append(entry)
def execute(self, sql, params=()):
start = time()
try:
return self.cursor.execute(sql, params)
finally:
sql = self.db.ops.last_executed_query(self.cursor, sql, params)
self.trace_entry(sql, start)
def executemany(self, sql, param_list):
start = time()
try:
return self.cursor.executemany(sql, param_list)
finally:
sql = '%s times: %s' % (len(param_list), sql)
self.trace_entry(sql, start)
django.db.backends.util.CursorDebugWrapper = TracingCursorDebugWrapper
then add the app to your INSTALLED_APPS settings, and set DEBUG_SQL_STACK = True in your settings.py file. Works with 1.2.
patch slightly cleaned up, but mostly documented in the FAQ