django - 将 create_or_get 与 DRF 一起使用的正确方法
问题描述
我有以下型号
class Word(models.Model):
"""Word object"""
word = models.CharField(max_length=255, unique=True)
def __str__(self):
return self.word
class Category(models.Model):
"""Category object"""
category = models.CharField(max_length=255, unique=True)
def __str__(self):
return self.category
class Group(models.Model):
"""Group object"""
user = models.ForeignKey(
settings.AUTH_USER_MODEL,
on_delete=models.CASCADE,
)
group = models.CharField(max_length=255)
categories = models.ManyToManyField("Category")
words = models.ManyToManyField("Word")
def __str__(self):
return self.group
class Puzzle(models.Model):
"""Puzzle object"""
user = models.ForeignKey(
settings.AUTH_USER_MODEL,
on_delete=models.CASCADE,
)
puzzle = models.CharField(max_length=255)
groups = models.ManyToManyField("Group")
def __str__(self):
return self.puzzle
以下观点
class WordViewSet(viewsets.ModelViewSet):
"""Manage words in the database"""
search_fields = ["word"]
filter_backends = (filters.SearchFilter,)
queryset = Word.objects.all()
serializer_class = serializers.WordSerializer
http_method_names = ["get", "post"]
class CategoryViewSet(viewsets.ModelViewSet):
"""Manage categories in the database"""
search_fields = ["category"]
filter_backends = (filters.SearchFilter,)
queryset = Category.objects.all()
serializer_class = serializers.CategorySerializer
http_method_names = ["get", "post"]
class GroupViewSet(viewsets.ModelViewSet):
"""Manage groups in the database"""
queryset = Group.objects.all()
serializer_class = serializers.GroupSerializer
permission_classes = [IsOwner, ]
def get_serializer_class(self):
"""Return appropriate serializer class"""
if self.action == "retrieve":
return serializers.GroupDetailSerializer
return self.serializer_class
def perform_create(self, serializer):
serializer.save(user=self.request.user)
class PuzzleViewSet(viewsets.ModelViewSet):
"""Manage puzzles in the database"""
queryset = Puzzle.objects.all()
serializer_class = serializers.PuzzleSerializer
permission_classes = [IsOwner, ]
def get_queryset(self):
queryset = Puzzle.objects.all()
user = self.request.query_params.get("user")
if user is not None:
queryset = Puzzle.objects.filter(user=user)
return queryset
def get_serializer_class(self):
"""Return appropriate serializer class"""
if self.action == "retrieve":
return serializers.PuzzleDetailSerialzer
return self.serializer_class
def perform_create(self, serializer):
serializer.save(user=self.request.user)
...以及以下序列化程序
class WordSerializer(serializers.ModelSerializer):
"""Serializer for Word objects"""
class Meta:
model = Word
fields = ("id", "word",)
read_only_fields = ("id",)
class CategorySerializer(serializers.ModelSerializer):
"""Serializer for Category objects"""
class Meta:
model = Category
fields = ("id", "category",)
read_only_fields = ("id",)
class GroupSerializer(serializers.ModelSerializer):
"""Serializer for Group objects"""
def validate(self, data):
if len(data["words"]) != 4:
raise ValidationError("Groups require exactly 4 words.")
return data
class Meta:
model = Group
fields = ("id", "group", "user", "categories", "words",)
read_only_fields = ("id", "user",)
class GroupDetailSerializer(GroupSerializer):
""" Detail Serializer for Group object"""
words = WordSerializer(many=True, read_only=True)
categories = CategorySerializer(many=True, read_only=True)
class PuzzleSerializer(serializers.ModelSerializer):
"""Serializer for Puzzle object"""
def validate(self, data):
if len(data["groups"]) != 4:
raise ValidationError("Puzzles require exactly 4 groups.")
return data
class Meta:
model = Puzzle
fields = ("id", "puzzle", "user", "groups")
read_only_fields = ("id", "user",)
class PuzzleDetailSerialzer(PuzzleSerializer):
"""Detail Serializer for Puzzle object"""
groups = GroupDetailSerializer(many=True, read_only=True)
我希望能够在不需要知道单词对象或类别对象的 id 的情况下对拼图对象进行发布请求。如果没有现有对象,则应将其创建并添加到组中,否则应将现有对象添加到组中。我的前端搜索这些单词和类别对象并使用单独的帖子请求创建它们似乎毫无意义。我希望能够一口气完成所有工作。我想我需要使用 create_or_get 但我正在寻找一些关于如何在这种情况下这样做的指导。
{
"puzzle": "my puzzle",
"groups": [
{
"group": "my animals",
"categories": ["animals"],
"words": ["cat", "dog", "turtle", "fish", ]
},
{
"group": "my kitchen",
"categories": ["kitchen"],
"words": ["cup", "plate", "fork", "knife"]
},
{
"group": "my people",
"categories": ["people"],
"words": ["man", "woman", "boy", "girl"]
},
{
"group": "my clothes",
"categories": ["clothes"],
"words": ["shirt", "pants", "jacket", "hat"]
}
]
}
解决方案
推荐阅读
- python - Python yield 关键字的意义和关于生成器的困惑?
- sql - SELECT 中的多个 WHERE
- excel - VBA 索引匹配函数
- java - 如何在 Java 的帮助下在运行时获取 testNG 方法名?
- c# - 编译器对与`using`指令冲突的命名空间感到困惑
- html - 如何从 Shopify 导航中隐藏特定标签?
- python - 检查给定列表中有多少单词出现在文本/字符串列表中
- visual-studio - 在 Visual Studio 2019 中未发现单元测试
- php - 对 REST API 的简单 PHP cURL 请求失败并出现错误:14077410
- r - 在 Ubuntu 18.04 上使用 gpuR(如何正确安装 OpenCL)