在 Django 中导致错误的有效 (?) JSON 数据必须作为字符串提供给前端并由 javascript 中的 JSON.parse() 转换 - 为什么?

Valid (?) JSON data causing errors in Django, must be served to frontend as string and converted by JSON.parse() in javascript - why?

我在我的 Django 目录中本地托管了一个 JSON 文件。它从该文件中提取到 views.py 中的视图,在其中像这样读入:

def Stops(request):
   json_data = open(finders.find('JSON/myjson.json'))
   data1 = json.load(json_data)  # deserialises it
   data2 = json.dumps(data1)  # json formatted string
   json_data.close()
   return JsonResponse(data2, safe=False)

在没有 (safe=False) 的情况下使用 JsonResponse returns 出现以下错误:

TypeError: In order to allow non-dict objects to be serialized set the safe parameter to False.

同样,使用 json.loads(json_data.read()) 而不是 json.load 会出现此错误:

json.decoder.JSONDecodeError: Expecting value: line 1 column 1 (char 0)

这让我感到困惑 - 我已经使用在线验证器验证了 JSON。当使用 safe=False 将 JSON 发送到前端时,到达的结果对象是一个字符串,即使在 javascript 中调用 .json() 之后也是如此:

fetch("/json").then(response => {
     return response.json();
     }).then(data => {
     console.log("data ", data); <---- This logs a string to console
...

然而,再往前一步并在字符串上调用 JSON.parse() 会将对象转换为我可以按预期使用的 JSON 对象

       data = JSON.parse(data);
       console.log("jsonData", data); <---- This logs a JSON object to console

但这个解决方案并不完整。

在这一点上,我认为最有可能的是源 JSON 有问题 -(在文件字符编码中?)或者 json.dumps() 没有做我认为它应该是什么,或者我不了解 Django API 的 JSON 响应功能,我不知道...

我已经达到了我对这个主题的了解的极限。如果您有什么智慧可以传授,我将不胜感激。

编辑:正如 Abdul 在下面的回答中一样,我将 JSON 重新格式化为带有 json.dumps(data1) 行

的字符串

工作代码如下:

def Stops(request):
   json_data = open(finders.find('JSON/myjson.json'))
   data = json.load(json_data)  # deserialises it
   json_data.close()
   return JsonResponse(data, safe=False)  # pass the python object here

让我们看看您的以下代码行:

json_data = open(finders.find('JSON/myjson.json'))
data1 = json.load(json_data)  # deserialises it
data2 = json.dumps(data1)  # json formatted string

您打开一个文件并在 json_data 中获取一个文件指针,解析其内容并在 data1 中获取一个 python 对象,然后将其 返回 转换为 JSON 字符串 并将其存储到 data2 中。有点多余吧?接下来,您将此 JSON 字符串传递给 JsonResponse,后者将进一步尝试将其序列化为 JSON!!意思是你然后在 JSON.

中的字符串中得到一个字符串

请尝试使用以下代码:

def Stops(request):
   json_data = open(finders.find('JSON/myjson.json'))
   data = json.load(json_data)  # deserialises it
   json_data.close()
   return JsonResponse(data, safe=False)  # pass the python object here

Note: function names in python should ideally be in snake_case not PascalCase, hence instead of Stops you should use stops. See PEP 8 -- Style Guide for Python Code