﻿id	summary	reporter	owner	description	type	status	component	version	severity	resolution	keywords	cc	stage	has_patch	needs_docs	needs_tests	needs_better_patch	easy	ui_ux
32226	QuerySet.explain(format='json') outputs repr'd JSON on PostgreSQL	Adam Johnson	Wu Haotian	"Call `.explain(format='json')` on a `QuerySet` on PostgreSQL, and the result *looks* like JSON, but isn't:

{{{
In [5]: User.objects.filter(is_staff=True).explain(format='json')
Out[5]: ""[{'Plan': {'Node Type': 'Seq Scan', 'Parallel Aware': False, 'Relation Name': 'auth_user', 'Alias': 'auth_user', 'Startup Cost': 0.0, 'Total Cost': 478.12, 'Plan Rows': 23, 'Plan Width': 157, 'Filter': 'is_staff'}}]""
}}}

One needs to use `ast.literal_eval` and `json.dumps` to get real JSON text that can be pasted into tools like [https://tatiyants.com/pev/ PostgreSQL explain viewer]:

{{{
In [10]: explain = User.objects.filter(is_staff=True).explain(format='json') ; print(json.dumps(ast.literal_eval(explain)))
[{""Plan"": {""Node Type"": ""Seq Scan"", ""Parallel Aware"": false, ""Relation Name"": ""auth_user"", ""Alias"": ""auth_user"", ""Startup Cost"": 0.0, ""Total Cost"": 478.12, ""Plan Rows"": 23, ""Plan Width"": 157, ""Filter"": ""is_staff""}}]
}}}

I guess this is because `psycopg2` loads the JSON as a Python list of dicts, then `SQLCompiler.explain_query` does `yield ' '.join(str(c) for c in row)`, which turns that list into its `repr()`."	Bug	closed	Database layer (models, ORM)	3.0	Normal	fixed		Tom Forbes Michael Christofides	Ready for checkin	1	0	0	0	0	0
