如何在常规django视图中向tastypie资源添加数据

时间:2013-03-09 23:04:19

标签: python django json rest tastypie

我在尝试在常规django视图中将tastypie资源包含在更大的json响应中时遇到了问题。我想让视图返回类似的东西(基于视图中生成的查询集,而不是典型的tastypie获取参数):

{
    "success": bool,
    "message": string,
    "error": string,
    "objects": [
        {
            "field_one": bar,
            "field_two": foo
        }
        ... more objects ...
    ]
}

其中,对象列表是序列化的tastypie资源列表,成功,消息和错误来自视图中的其他位置。

现在,我无法弄清楚如何在更大的dict构建之前避免将序列化资源转换为字符串,所以我现在有这样的事情:

{
    "success": bool,
    "message": string,
    "error": string,
    "objects": [
        "{"field_one": bar, "field_two": foo..."}",
        "{"field_one": baz, "field_two": foobar..."}",
        ...
    ]
}

这一点的重点是保持模型json表示一致,以最小化直接使用tastypie api和使用这些视图中返回的数据之间的摩擦。我认为解决方案是以某种方式在每个资源上使用full_dehydrate方法而不对其进行序列化,然后将它们添加到更大的dict,然后序列化该dict,但我不确定要使用哪个序列化程序。或者,也许有更好的方法。

1 个答案:

答案 0 :(得分:1)

通常情况下,写这篇文章有助于我找到一个临时解决方案。也许有人会对如何做得更好有一些意见。

我正在使用它来为序列化准备一个查询集:

def serialize_queryset(resource_class, queryset):
    # hand me a queryset, i give you dehydrated resources
    resource = resource_class()
    dd = {}

    # make meta
    dd['meta'] = {}
    dd['meta']['limit'] = 1000
    dd['meta']['next'] = None
    dd['meta']['offset'] = 0
    dd['meta']['previous'] = None
    dd['meta']['total_count'] = len(queryset)

    # objects
    dd['objects'] = []
    for obj in queryset:
        bundle = resource.build_bundle(obj=obj)
        dehydrated_obj = resource.full_dehydrate(bundle)
        dd['objects'].append(dehydrated_obj)

    # return dict
    return dd

我使用tastypie.serializer中的Serializer。并且在示例视图中使用它就像:

from tastypie.serializer import Serializer

serializer = Serializer()

def my_view(request):

    #... do some other view stuff ...

    # prepare a queryset for serialization
    queryset = MyModel.objects.filter(is_cool=True)
    data = serialize_queryset(MyModel, queryset)

    # add in custom stuff, determined earlier in the view somewhere
    data['success'] = success
    data['message'] = message
    data['error'] = error

    # serialize and return response
    data = serializer.serialize(data)
    return HttpResponse(data, mimetype='application/json')

这似乎有效。也许你看到这种方法有些不好,或者是一种改进它的方法?