【问题标题】:How to set an HTTP header for a JSON message from within a django-piston handler?如何在 django-piston 处理程序中为 JSON 消息设置 HTTP 标头?
【发布时间】:2011-04-09 00:53:56
【问题描述】:

在活塞处理程序中,我需要将 django.db.models.query.QuerySet 作为正确的 JSON 消息(反映基础模型和查询)返回,同时还添加我自己的 HttpResponse 标头。到目前为止,我可以做一个或另一个,但不能同时做(并获得一个看起来正确的 JSON 响应)。

以下生成正确的 JSON 格式响应,但没有添加 HttpResponse 标头(未显示):

class PollHandlerSearch(BaseHandler):
    allowed_methods = ('POST')
    model = Poll
    fields = ('id', 'question', 'pub_date')
    KEYS =  ( 'question', 'start-date', 'end-date' )

    def create(self, request):
        post = Poll.objects.all()
        for skey in self.KEYS:
            if len(post) and request.POST.has_key(skey) and len(request.POST[skey]):
                if skey == self.KEYS[0]:
                        post = post.filter(question__icontains=request.POST[skey])
                elif skey == self.KEYS[1]:
                        post = post.filter(pub_date__gte=request.POST[skey])
                elif skey == self.KEYS[2]:
                        post = post.filter(pub_date__lte=request.POST[skey])
        return post

生成格式正确的 JSON 消息:

[
    {
        "pub_date": "2010-08-23 22:15:07", 
        "question": "What's up?", 
        "id": 1
    }
]

下面实现了一个带有添加头的 HttpResponse 并生成一个 JSONish 的响应,但这不是预期或想要的,而且不反映 django 的“DateTimeAwareJSONEncoder”所做的任何事情(由活塞的 JSONEmitter 使用)。

class PollHandlerSearch(BaseHandler):
    allowed_methods = ('POST')
    model = Poll
    fields = ('id', 'question', 'pub_date')
    KEYS =  ( 'question', 'start-date', 'end-date' )

    def create(self, request):
        resp = HttpResponse()
        post = Poll.objects.all()
        for skey in self.KEYS:
            if len(post) and request.POST.has_key(skey) and len(request.POST[skey]):
                if skey == self.KEYS[0]:
                        post = post.filter(question__icontains=request.POST[skey])
                elif skey == self.KEYS[1]:
                        post = post.filter(pub_date__gte=request.POST[skey])
                elif skey == self.KEYS[2]:
                        post = post.filter(pub_date__lte=request.POST[skey])
        json_serializer = serializers.get_serializer("json")()
        json_serializer.serialize(post, ensure_ascii=False, indent=4, stream=resp)
        resp['MYHEADER'] = 'abc123'
        return resp

导致格式不正确的 JSONish 消息:

[
    {
        "pk": 1, 
        "model": "polls.poll", 
        "fields": {
            "pub_date": "2010-08-23 22:15:07", 
            "question": "What's up?"
        }
    }
]

这毫无疑问会发生,因为我正在做自己的 JSON 序列化,绕过活塞的 JSONEmitter,因此无论它做什么来正确渲染“post”。

我一直在研究活塞的emitters.py,但基本上无法理解它(我在 OOP / Python / django / 活塞方面还很陌生)。如何让活塞传递格式正确的 JSON 消息,其中包含我提供的标头补充的 HTTP 标头?

【问题讨论】:

    标签: django django-piston


    【解决方案1】:

    您可以继承piston.resource.Resource,并在__call__ 方法中添加您想要的任何标题。 从活塞.resource 导入资源

    class MyResource(Resource):
        def __call__(self, request, *args, **kwargs):
            resp = super(MyResource, self).__call__(request, *args, **kwargs)
            resp['HEADER'] = "abc123"
            return resp
    

    然后,在你的 urls.py 中:

    def BasicResource(handler):
        return resource.MyResource(handler=handler, authentication=basic)
    
    your_handler = BasicResource(YourHandlerClass)
    another_handler = BasicResource(AnotherHandlerClass)
    

    【讨论】:

    • 感谢您的回答。 Piston 在Resource.__call__ 中创建新响应对象的方式使得从处理程序中干净地获取响应标头到客户端有点困难。我在我的应用程序中设置了一个模式,我在请求对象上设置了一个属性,然后在调用__call__ 后读取它。 if hasattr(request, 'num_objects'): response['X-EB-Num-Objects'] = request.num_objects 不是我最好的作品。
    • @BobVanZant:我的工作也是如此。令人讨厌和丑陋,但工作......就像大多数活塞一样。
    猜你喜欢
    • 1970-01-01
    • 2013-08-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-02-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多