如何处理Django Rest Framework中的模型更改?

时间:2017-05-08 15:45:24

标签: django rest api django-rest-framework

这不是特定用例的问题,而是我在使用API​​时体验到的一些问题,特别是使用Django和Django Rest Framework。

几个月前,我为客户的项目维护的API存在问题。

我们假设我们有以下型号:

class Person:
    first_name = models.CharField(max_length=100)
    last_name = models.CharField(max_length=100)

然后,相应的序列化器:

class PersonSerializer(serializers.ModelSerializer):
    class Meta:
        model = Person
        fields = '__all__'

当然,它对应的ViewSet和路由指向它:

http://localhost:8000/api/v1/persons/

请注意,这是我的API的第一个版本。

此时一切都还好,对吧?

现在,我的客户要求我们需要单独收到人的姓名而不是姓名...

按照惯例,我必须将我的模型改为:

class Person:
    full_name = models.CharField(max_length=200)

使用此版本的API有3个不同的客户端(移动应用程序)。显然,我不想更改我的API,而是希望将新方法用于新版本。

但是第一个版本的Serializer与模型相结合,所以此时API的第一个版本已经改变

我希望在下面的答案中看到你们是如何处理Django中的这个问题的,以及我应该采用相同的堆栈为下一个项目采取的方式。

编辑:我的问题是要了解是否更好地将API与模型分离。我已经提出了一个非常基本的例子,但有些情况会使事情变得复杂得多。例如,我需要修改M2M关系以使用through选项,以便向中间表添加更多字段。

1 个答案:

答案 0 :(得分:1)

这类问题可被标记为"推荐smth",但无论如何。

首先,您需要使用full_name字段扩展模型。如果您需要能够从api写入full_name提供的模型,那么您需要扩展到字段,否则您可以处理property

@property
def full_name(self):
    return '{} {}'.format(self.first_name, self.last_name)

然后您还可以在序列化程序中包含字段

class PersonSerializer(serializers.ModelSerializer):
    full_name = serializers.CharField()  # if you have property
    class Meta:
        model = Person
        fields = '__all__'

由于您将字段名称和序列化程序字段名称匹配,因此您不必担心。

因此,增加一个领域不会打破你的客户并满足你的大客户。