Skip to content

Commit 1cd51a6

Browse files
committed
Fix #1621: Do not crash when encountering unexpected data in the request
1 parent 4d5df40 commit 1cd51a6

File tree

4 files changed

+31
-8
lines changed

4 files changed

+31
-8
lines changed

debug_toolbar/panels/request.py

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -26,9 +26,11 @@ def nav_subtitle(self):
2626
def generate_stats(self, request, response):
2727
self.record_stats(
2828
{
29-
"get": get_sorted_request_variable(request.GET),
30-
"post": get_sorted_request_variable(request.POST),
31-
"cookies": get_sorted_request_variable(request.COOKIES),
29+
"get": get_sorted_request_variable(request.GET, source="GET"),
30+
"post": get_sorted_request_variable(request.POST, source="POST"),
31+
"cookies": get_sorted_request_variable(
32+
request.COOKIES, source="COOKIES"
33+
),
3234
}
3335
)
3436

debug_toolbar/utils.py

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -229,14 +229,17 @@ def getframeinfo(frame, context=1):
229229
return (filename, lineno, frame.f_code.co_name, lines, index)
230230

231231

232-
def get_sorted_request_variable(variable):
232+
def get_sorted_request_variable(variable, *, source):
233233
"""
234234
Get a sorted list of variables from the request data.
235235
"""
236-
if isinstance(variable, dict):
237-
return [(k, variable.get(k)) for k in sorted(variable)]
238-
else:
239-
return [(k, variable.getlist(k)) for k in sorted(variable)]
236+
try:
237+
if isinstance(variable, dict):
238+
return [(k, variable.get(k)) for k in sorted(variable)]
239+
else:
240+
return [(k, variable.getlist(k)) for k in sorted(variable)]
241+
except TypeError:
242+
return [(f"<{source}>", variable)]
240243

241244

242245
def get_stack(context=1):

docs/changes.rst

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,10 @@ Change log
33

44
* Removed third party panels which have been archived on GitHub.
55
* Added Django 4.1a1 to the CI matrix.
6+
* Stopped crashing when ``request.GET`` and ``request.POST`` are neither
7+
dictionaries nor ``QueryDict`` instances. Using anything but ``QueryDict``
8+
instances isn't a valid use of Django but, again, django-debug-toolbar
9+
shouldn't crash.
610

711
3.4.0 (2022-05-03)
812
------------------

tests/panels/test_request.py

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,20 @@ def test_dict_for_request_in_method_post(self):
8585
self.assertIn("foo", content)
8686
self.assertIn("bar", content)
8787

88+
def test_list_for_request_in_method_post(self):
89+
"""
90+
Verify that the toolbar doesn't crash if request.POST contains unexpected data.
91+
92+
See https://github.com/jazzband/django-debug-toolbar/issues/1621
93+
"""
94+
self.request.POST = [{"a": 1}, {"b": 2}]
95+
response = self.panel.process_request(self.request)
96+
self.panel.generate_stats(self.request, response)
97+
# ensure the panel POST request data is processed correctly.
98+
content = self.panel.content
99+
self.assertIn("&lt;POST&gt;", content)
100+
self.assertIn("[{&#x27;a&#x27;: 1}, {&#x27;b&#x27;: 2}]", content)
101+
88102
def test_namespaced_url(self):
89103
self.request.path = "/admin/login/"
90104
response = self.panel.process_request(self.request)

0 commit comments

Comments
 (0)