Django REST框架:非模型序列化程序

内容来源于 Stack Overflow,并遵循CC BY-SA 3.0许可协议进行翻译与使用

  • 回答 (1)
  • 关注 (0)
  • 查看 (23)

我是Django REST框架的初学者,需要您的建议。我正在开发一个Web服务。该服务必须为其他服务提供REST接口。我需要实现的REST接口并不直接使用我的模型(我指的是GET、PUT、POST、DELETE操作)。相反,它为其他服务提供了一些计算结果。在请求时,我的服务会进行一些计算,只返回结果(不将结果存储在自己的数据库中)。

下面是我对如何实现REST接口的理解。如果我错了,请纠正我。

  1. 创建类来进行计算。命名为“CalcClass”。CalcClass在其工作中使用模型。
- Params necessary for the calculations are passed to the constructor.  
- Implement the calc operation. It returns results as 'ResultClass'.  

  1. 创建结果类。
- Derived from object.  
- It just only has attributes containing the calc results.  
- One part of the calc results is represented as tuple of tuples. As I understand, it would be better for further serialization to implement a separate class for those results and add list of such objects to ResultClass.  

  1. 为ResultClass创建序列化程序。
- Derive from serializers.Serializer.  
- The calc results are read-only, so use mostly Field class for fields, instead of specialized classes, such as IntegerField.  
- I should not impl save() method neither on ResultClass, nor on Serializer, because I am not going to store the results (I just want to return them on request).  
- Impl serializer for nested results (remember tuple of tuples mentioned above).  

  1. 创建视图以返回计算结果。
- Derive from APIView.  
- Need just get().  
- In get() create CalcClass with params retrieved from the request, call its calc(), get ResultClass, create Serializer and pass the ResultClass to it, return Response(serializer.data).  

  1. URL
- There is no api root in my case. I should just have URLs to get various calc results (calc with diff params).  
- Add calling format\_suffix\_patterns for api browsing.  

我错过了什么吗?这种方法一般是正确的吗?

提问于
用户回答回答于

Django-REST框架运行良好,即使不将其与模型绑定。你的方法听起来不错,但我相信你可以修剪一些步骤,让一切正常工作。

例如,REST框架附带了一些内置的呈现器。它可以将JSON和XML返回给API使用者。还可以通过安装所需的python模块来启用YAML。Django-REST-框架将输出任何基本对象,如dict、list和tuple,而不需要额外的工作。

因此,基本上只需创建接受参数的函数或类,执行所有所需的计算,并以元组的形式将其结果返回给RESTAPI视图。如果JSON和/或XML适合您的需要,Django-REST-框架将负责您的序列化。

在本例中,可以跳过步骤2和步骤3,只需使用一个类进行计算,使用一个类表示API使用者。

这里有几个片段可以帮助你解决这个问题:

请注意,我还没有测试过这个。它只是作为一个例子,但它应该有效:)

CalcClass:

class CalcClass(object):

    def __init__(self, *args, **kw):
        # Initialize any variables you need from the input you get
        pass

    def do_work(self):
        # Do some calculations here
        # returns a tuple ((1,2,3, ), (4,5,6,))
        result = ((1,2,3, ), (4,5,6,)) # final result
        return result

其余视图:

from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import status

from MyProject.MyApp import CalcClass


class MyRESTView(APIView):

    def get(self, request, *args, **kw):
        # Process any get params that you may need
        # If you don't need to process get params,
        # you can skip this part
        get_arg1 = request.GET.get('arg1', None)
        get_arg2 = request.GET.get('arg2', None)

        # Any URL parameters get passed in **kw
        myClass = CalcClass(get_arg1, get_arg2, *args, **kw)
        result = myClass.do_work()
        response = Response(result, status=status.HTTP_200_OK)
        return response

你的urls.py:

from MyProject.MyApp.views import MyRESTView
from django.conf.urls.defaults import *

urlpatterns = patterns('',
    # this URL passes resource_id in **kw to MyRESTView
    url(r'^api/v1.0/resource/(?P<resource_id>\d+)[/]?$', login_required(MyRESTView.as_view()), name='my_rest_view'),
    url(r'^api/v1.0/resource[/]?$', login_required(MyRESTView.as_view()), name='my_rest_view'),
)

[
  [
    1, 
    2, 
    3
  ], 
  [
    4, 
    5, 
    6
  ]
]

希望这能帮到你。

扫码关注云+社区