简体   繁体   English

Django Rest Framework:在JSON OBJECT中循环

[英]Django Rest Framework: Loop inside JSON OBJECT

Hi Guys I'm new to Django and Python... I'm using REST Framework to develop some webservices. 嗨大家我是Django和Python的新手......我正在使用REST Framework来开发一些web服务。 I want to loop through all the orders of a JSON item. 我想循环遍历JSON项的所有订单。 The request from javascript is done in this way: 来自javascript的请求以这种方式完成:

    function TestDjangoPostWithNoCsrlTokenAndWithMultipleObjectsJson() {

    var JSONObject = new Object();
    JSONObject.Orders = [];
    JSONObject.Orders.push({ id: 1, Name: 'Name1', Description: 'Description1' });
    JSONObject.Orders.push({ id: 2, Name: 'Name2', Description: 'Description1' });
    JSONObject.Orders.push({ id: 3, Name: 'Name3', Description: 'Description1' });
    console.log(JSON.stringify(JSONObject));
    $.ajax
  ({
      type: "POST",
      url: URL_PostOrdersMultipleObjects,
      headers: {
          "Authorization": "Basic " + btoa("xxx" + ":" + "xxx")
      },
      data: JSONObject,
      dataType: 'json',      

      success: function (data, status, xhr) {
       console.log(JSON.stringify(data));
          if (xhr.readyState == 4) {
              if (xhr.status == 201) {
                  console.log("Created");
              }
          } else {
              console.log("NoGood");
          }
      },
      complete: function (xhr) {
      },
      error: function (xhr, ajaxOptions, thrownError) {
          console.log(xhr.status);
          console.log(thrownError);
      }
  });


}

On Django side, I have... 在Django方面,我有......

  @api_view(['GET', 'POST'])
def JSONPostTest(request):
    if request.method == 'POST':  
        stream = io.BytesIO(request.body)
        obj = JSONParser().parse(stream)  

        for order in obj['Orders']:     # First Example

            serializer = QASerializer(data=order)
            if serializer.is_valid():
               serializer.save()
            else :
               return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)   

        return Response('OK', status=status.HTTP_201_CREATED)           
    else:
        return Response('OK', status=status.HTTP_201_CREATED) 

If In javascript i stringify my object before to send it the above code works fine. 如果在javascript中我在发送之前对我的对象进行字符串化,则上面的代码工作正常。 The problems is when I don't stringify. 问题是当我没有字符串化时。

If I stringify 如果我字符串化

request.body = 
b'{"Orders":[{"id":1,"Name":"Name1","Description":"Description1"},{"id":2,"Name":"Name2","Description":"Description2"},{"id":3,"Name":"Name3","Description":"Description3"}]}'

if I don't stringify 如果我没有字符串化

request.body
b'Orders%5B0%5D%5Bid%5D=1&Orders%5B0%5D%5BName%5D=Name1&Orders%5B0%5D%5BDescription%5D=Description1&Orders%5B1%5D%5Bid%5D=2&Orders%5B1%5D%5BName%5D=Name2&Orders%5B1%5D%5BDescription%5D=Description1&Orders%5B2%5D%5Bid%5D=3&Orders%5B2%5D%5BName%5D=Name3&Orders%5B2%5D%5BDescription%5D=Description1'

and

request.data
<QueryDict: {'Orders[1][Description]': ['Description1'], 'Orders[2][id]': ['3'], 'Orders[0][Name]': ['Name1'], 'Orders[0][Description]': ['Description1'], 'Orders[2][Description]': ['Description1'], 'Orders[1][id]': ['2'], 'Orders[0][id]': ['1'], 'Orders[1][Name]': ['Name2'], 'Orders[2][Name]': ['Name3']}>

I can stringify no problem on that. 我可以在字面上没有问题。 But I want to understand if it's possible to obtain the same result without stringifing starting from the QueryDict I have. 但我想了解是否有可能从我没有的QueryDict开始获得相同的结果。

Thank you 谢谢

You've not only constructed your JSON object in an unnecessarily verbose and complex way, you're also using the wrong data structure. 您不仅以不必要的冗长和复杂的方式构造了JSON对象,而且还使用了错误的数据结构。 If you want to iterate something, it should be an array (which maps to a list in Python), not an object (which maps to a dict). 如果你想迭代一些东西,它应该是一个数组(映射到Python中的列表),而不是一个对象(映射到一个字典)。 Your JS code should look like this: 您的JS代码应如下所示:

JSONObject.Orders = [];
JSONObject.Orders.push({id: 1, Name: 'Name1', Description: 'Description1'});
JSONObject.Orders.push({id: 2, Name: 'Name2', Description: 'Description1'});
JSONObject.Orders.push({id: 3, Name: 'Name3', Description: 'Description1'});

(You could actually make that more compact by defining the objects inline with the array, but this is at least clearer for now.) (你可以通过定义与数组内联的对象来实现更紧凑,但现在至少更清楚了。)

Now, it's simple to iterate in Python: 现在,在Python中迭代很简单:

for obj in jsondata['Orders']:
    ...

Since you write you have a Serializer for Order I assume it is also a model on your backend and you would like to store it in the database. 既然你写了你有一个Serializer for Order我认为它也是你后端的模型,你想将它存储在数据库中。 In that case I would not bother to manually deserialize the list of orders but let django-restframework unpack the nested child objects along with the parent. 在这种情况下,我不打算手动反序列化订单列表,但让django-restframework将嵌套的子对象与父对象一起解包。

Have a look here: https://stackoverflow.com/a/28246994/640916 看看这里: https//stackoverflow.com/a/28246994/640916

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM