2016-11-21 173 views
4

我正在使用python和django来开发一些REST API。我有一个关于请求调用返回的JSON unicode字符串的问题。所以,我做这样的事情:json对象由http响应返回

resp = requests.get(self.url) 
if resp.status_code is status.HTTP_200_OK: 
    obj = json.loads(resp.json()) 

有了这个,我可以遍历条目:

for o in obj: 
    print o 

这将打印类似:

{u'pk': 1, u'model': u'aslapp.imagetypemodel', u'fields': {u'type': u'PNG'}} 
{u'pk': 2, u'model': u'aslapp.imagetypemodel', u'fields': {u'type': u'JPG'}} 

但是,我读了resp.json()调用应该在内部调用这个json.loads()方法,并将照顾编码的东西。然而,只是在做:

obj = resp.json() 
for o in obj: 
    print o 

只是遍历unicode字符串中的每个字符。那么我是否应该通过loads方法再次运行它,如果我想遍历JSON条目?遍历resp.json()返回的所有JSON记录的正确方法是什么?

+0

我有点困惑 - 'requests.get'与django或[requests](http://docs.python-requests.org/en/master/)有关? – dahrens

回答

5

你是对的,resp.json()确实为你打电话json.loads()

因此,如果resp.json()返回一个字符串,则表明API已经将json编码了两次数据。例如,它将返回"{\"pk\": 1}"而不是{"pk": 1}

如果您对API没有任何控制权,那么您必须对其进行解码两次以获取Python对象。

+0

没错。所以在Django方面,返回的数据是'data = serializers.serialize(“json”,types)return Response(data)' – Luca

+1

@Luca Django也有一个'JsonResponse',你可以直接传递类似于dicts或lists的对象。 – schwobaseggl

+2

如果响应来自DRF,那么它会为您序列化一些东西;正如DRF文档所指出的那样,您应该传递Python原语(例如字典和列表)而不是已经呈现的JSON。使用标准的HttpResponse,或者使用DRF的序列化器而不是Django的序列化器。 –