2
votes

Comment sérialiser des champs liés à un modèle via un autre modèle?

Mes modèles sont les suivants:

class Question(models.Model):
    content = models.CharField(
        max_length=1000,
        blank=False,
        default='',
        )

    def __str__(self):
        return self.content


class OptionGroup(models.Model):

    question = models.ForeignKey(
        'Question',
        on_delete=models.CASCADE,
        default='',
        )

    options = models.ManyToManyField('Option')


class Option(models.Model):

    content = models.CharField(
        max_length=1000,
        blank=False,
        default='',
        )

J'essaye de créer un sérialiseur de question qui sérialisera Question.content et tout le Option.content associé sans afficher aucun champ d'OptionGroup. Comment faire cela?


2 commentaires

pourquoi vous utilisez OptionGroup? vous pouvez mettre des options dans le modèle Question


Il existe d'autres champs sur OptionGroup que j'ai omis par souci de simplicité.


3 Réponses :


2
votes

Vous pouvez sérialiser des modèles associés en utilisant des sérialiseurs imbriqués comme celui-ci:

{
    'content': 'some content',  # your Question
    'options': [
        {'content': 'some content'},  # related Option
        {'content': 'some other content'},  # related Option
        ...
    ],
}

Ce qui donnera le résultat suivant:

class OptionSerializer(serializers.ModelSerializer):
    class Meta:
        model = Option
        fields = ('content',)

class QuestionSerializer(serializers.ModelSerializer):
    options = OptionSerializer(many=True, read_only=True)

    class Meta:
        model = Question
        fields = ('content', 'options')

Vous pouvez Pour en savoir plus sur les sérialiseurs imbriqués, cliquez ici .

p>


1 commentaires

Avez-vous vu la structure du modèle? L'option n'est pas directement liée à la question. Ça ne marche pas pour moi comme ça.



0
votes

modèles:

class OptionSerializer(serializers.ModelSerializer):

    class Meta:
        model = Option
        exclude = ('id',)


class QuestionSerializer(serializers.ModelSerializer):
    options = serializers.SerializerMethodField(read_only=True)

    def get_options(self, obj):
        options = obj.get_options()
        return OptionSerializer(options, many=True).data

    class Meta:
        model = Question
        fields = "__all__"

sérialiseurs

class OptionGroup(models.Model):

    question = models.ForeignKey(
        'Question',
        on_delete=models.CASCADE,
        default='',
        related_name='question_options'
        )

    options = models.ManyToManyField('Option')

class Question(models.Model):
    content = models.CharField(
        max_length=1000,
        blank=False,
        default='',
        )
    # options = models.ManyToManyField('Option', through='OptionGroup')
    def get_options(self):
        options = self.question_options.all().values('options')
        option_ids = []
        for option in options:
            option_ids.append(option['options'])
        return Option.objects.filter(id__in=option_ids)
    def __str__(self):
        return self.content

class Option(models.Model):

    content = models.CharField(
        max_length=1000,
        blank=False,
        default='',
        )

    def __str__(self):
        return self.content


1 commentaires

Beaucoup d'erreurs dans votre réponse. Vous avez déclaré OptionSerializer mais ne l'avez pas utilisé. Vous utilisez un champ question_options mais il n'est pas défini sur ce modèle particulier (en supposant que vous vouliez dire optiongroup_set ). Mais toujours après avoir corrigé ceux-ci, ce n'est toujours pas dans le format que je souhaite. Le format que je veux est ce que @Stevy a donné ci-dessus mais sa réponse est également fausse car l'option n'est pas directement liée à la question.



0
votes

Créez un champ SerializerMethod et définissez-le en conséquence:

serializers.py

from rest_framework import serializers

from diagnosisApp.models import Question, Option


class OptionSerializer(serializers.ModelSerializer):

    class Meta:
        model = Option
        fields = ('id', 'content')


class QuestionSerializer(serializers.ModelSerializer):
    options = serializers.SerializerMethodField()

    class Meta:
        model = Question
        fields = ('content', 'options')

    def get_options(self, obj):
        selected_options = Option.objects.filter(
            optiongroup__question=obj).distinct()
        return OptionSerializer(selected_options, many=True).data


0 commentaires