diff --git a/silk/migrations/0009_sqlquery_query_structure.py b/silk/migrations/0009_sqlquery_query_structure.py new file mode 100644 index 00000000..46201a22 --- /dev/null +++ b/silk/migrations/0009_sqlquery_query_structure.py @@ -0,0 +1,18 @@ +# Generated by Django 3.2.16 on 2022-10-21 15:55 + +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('silk', '0008_sqlquery_analysis'), + ] + + operations = [ + migrations.AddField( + model_name='sqlquery', + name='query_structure', + field=models.TextField(default=''), + ), + ] diff --git a/silk/models.py b/silk/models.py index e7490d5c..ad4fe0fe 100644 --- a/silk/models.py +++ b/silk/models.py @@ -237,6 +237,7 @@ def bulk_create(self, *args, **kwargs): class SQLQuery(models.Model): query = TextField() + query_structure = TextField(default='') start_time = DateTimeField(null=True, blank=True, default=timezone.now) end_time = DateTimeField(null=True, blank=True) time_taken = FloatField(blank=True, null=True) diff --git a/silk/sql.py b/silk/sql.py index 197a999d..5a8feec7 100644 --- a/silk/sql.py +++ b/silk/sql.py @@ -81,6 +81,7 @@ def execute_sql(self, *args, **kwargs): if _should_wrap(sql_query): query_dict = { 'query': sql_query, + 'query_structure': q, 'start_time': timezone.now(), 'traceback': tb } diff --git a/silk/templates/silk/sql.html b/silk/templates/silk/sql.html index 2b5b970d..e59bb03b 100644 --- a/silk/templates/silk/sql.html +++ b/silk/templates/silk/sql.html @@ -41,7 +41,7 @@ height: 20px; } - tr.data-row:hover { + tr.data-row:hover, tr.data-row.highlight { background-color: rgb(51, 51, 68); color: white; cursor: pointer; @@ -108,10 +108,14 @@ Tables Num. Joins Execution Time (ms) + Num. Duplicates {% for sql_query in items %} - {{ sql_query.tables_involved|join:", " }} {{ sql_query.num_joins }} {{ sql_query.time_taken | floatformat:6 }} + {{ sql_query.num_duplicates }} {% endfor %} @@ -151,8 +156,20 @@ - - + {% endblock %} diff --git a/silk/views/sql.py b/silk/views/sql.py index f3a69072..46c18cc9 100644 --- a/silk/views/sql.py +++ b/silk/views/sql.py @@ -1,3 +1,5 @@ +from collections import defaultdict + from django.shortcuts import render from django.utils.decorators import method_decorator from django.views.generic import View @@ -20,10 +22,16 @@ def get(self, request, *_, **kwargs): 'request': request, } if request_id: + query_duplicates = defaultdict(lambda: -1) silk_request = Request.objects.get(id=request_id) query_set = SQLQuery.objects.filter(request=silk_request).order_by('-start_time') for q in query_set: q.start_time_relative = q.start_time - silk_request.start_time + query_duplicates[q.query_structure] += 1 + structures = list(query_duplicates.keys()) + for q in query_set: + q.num_duplicates = query_duplicates[q.query_structure] + q.duplicate_id = structures.index(q.query_structure) page = _page(request, query_set) context['silk_request'] = silk_request if profile_id: