创建能够序列化 Django Rest Framework 中基本模型的所有子类的通用序列化程序的最佳方法是什么?

What's the best way to create a generic serializer which is able to serialize all the subclasses of the base model in Django Rest Framework?

我目前正在开发一个通知系统,它将通过 API.

传递许多不同类型的通知

我有一个名为 BaseNotification 的基本通知 class。这是代码:

class BaseNotification(models.Model):
    message = models.CharField(max_length=500)
    seen = models.BooleanField(default=True)
    
    class Meta:
        abstract = True

我想子class这个模型来创建不同的通知变体:

class InvitationNotification(BaseNotification):
    invited_user = models.ForeignKey(User, on_delete=models.CASCADE)
    campagin = models.ForeignKey(Campagin, on_delete=models.CASCADE)
    # ... the rest of specific fields

class ChatMessageNotification(BaseNotification):
    contact = models.ForeignKey(User, on_delete=models.CASCADE)
    chat_room = models.ForeignKey(SomeSortOfChatRoomWhichIsNotImplementedYet, on_delete=models.CASCADE)
    # ... the rest of specific fields

如您所见,这些变体中的每一个都有一些与之关联的元数据。前端开发人员将能够使用这些元数据创建用户交互(例如,在聊天消息的情况下,前端开发人员会将用户重定向到聊天室)

我想通过一个统一的方式列出所有这些通知 API。为此,我需要一个序列化程序来将对象序列化为 json 但我不想为每个对象都有一个单独的序列化程序。理想情况下,我想要一个通用的序列化程序,它能够序列化所有类型的通知,并根据传入的通知对象的类型生成不同的 json 输出。(它可能在后台使用其他序列化程序)。

也许我走错了路,但最终目标是通过一个统一的 API.

传递通知及其所有元数据

我真的需要你的建议和帮助。提前谢谢大家。

我终于自己弄明白了。我的最终目标是为前端开发人员提供一些元数据,以便他可以根据通知类型实现用户交互。

我用一个JSONField简单的解决了这个问题。这很好用,这是我唯一需要的东西。

models.py

class Notification(models.Model):
    NEW_MEMBER_JOINED = 'NEW_MEMBER_JOINED'
    INVITATION = 'INVITATION'
    TEXT = 'TEXT'
    NEW_POST_CREATED = 'NEW_POST_CREATED'
    NEW_MESSAGE = 'NEW_MESSAGE'
    NEW_CAMPAIGN_CONTENT = 'NEW_CAMPAIGN_CONTENT'
    NEW_COMMENT = 'NEW_COMMENT'
    
    target = models.ForeignKey(User, on_delete=models.CASCADE, related_name='notifications')
    text = models.CharField(max_length=300)
    type = models.CharField(max_length=255)
    date_created = models.DateTimeField(auto_now_add=True)
    seen = models.BooleanField(default=False)
    metadata = models.JSONField(null=True, blank=True)

    def __str__(self) -> str:
        return f"[{self.type}] {self.text}"

serializers.py

class NotificationSerializer(serializers.ModelSerializer):
    class Meta:
        model = Notification
        fields = '__all__'
        read_only_fields = [
            'text', 'type', 'metadata', 'date_created', 'seen'
        ]

就我而言,此解决方案效果最好。