Сериализация расширенной модели пользователя в Django

Я расширяю пользовательскую модель django auth в модели Profile:

from django.db import models
from django.contrib.auth.models import User

class Profile(models.Model):
    user = models.OneToOneField(User, on_delete=models.CASCADE)
    activity = models.IntegerField(default=500)

    def _str_(self):
        return self

В моих представлениях я получаю текущего пользователя auth и получаю связанный с ним профиль:

@api_view(['GET'])
@permission_classes([IsAuthenticated])
def getUserProfile(request):
    profile = Profile.objects.get(user = request.user)
    serializer = profileSerializer(profile, many=False)
    return Response(serializer.data)

Вот мой код сериализаторов:

from rest_framework import serializers
from .models import Profile

class profileSerializer(serializers.ModelSerializer):
    class Meta:
        model = Profile
        fields = ('first_name', 'activity')

Я получаю ошибку, что объект Profie не имеет атрибута first_name, но когда я заменяю 'first_name' на 'user' я получаю только id пользователя, поэтому я хочу показать first_name также.

Спасибо

Поле OneToOneField связывает ваше поле user в модели Profile с объектом User, который имеет атрибут first_name, но в таблице Profile это поле user является просто номером, который говорит, какой объект User это. Чтобы получить доступ к первому имени, вы можете сделать следующее:

from rest_framework import serializers
from .models import Profile

class profileSerializer(serializers.ModelSerializer):
    class Meta:
        model = Profile
        fields = '__all__'

Тогда в вашем шаблоне вы можете отобразить first_name следующим образом, предполагая, что вы передаете ему person, где person является экземпляром модели Profile:

{{ person.user.first_name }}

Я также думаю, что было бы менее запутанно использовать другое имя для поля, а не user. Назовите его персоной, например:

from django.db import models
from django.contrib.auth.models import User

class Profile(models.Model):
    person = models.OneToOneField(User, on_delete=models.CASCADE)
    activity = models.IntegerField(default=500)

    def _str_(self):
        return self

Попробуйте это:

from django.contrib.auth.models import User

class profileSerializer(serializers.ModelSerializer):
    first_name = serializers.CharField(max_length=200, read_only=True)

    class Meta:
        model = Profile
        fields = ('user', 'first_name', 'activity')

    def get_first_name(self, obj):
        return User.objects.filter(id=obj.user.id).first().values_list('first_name', flat=True).last()

Я смог показать нужные мне поля, используя Django depth в сериализаторе

from rest_framework import serializers
from .models import Profile
from django.contrib.auth.models import User


class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = ('first_name', 'last_name')


class profileSerializer(serializers.ModelSerializer):
    user = UserSerializer()
    class Meta:
        model = Profile
        fields = ('activity','user')
        depth=1
Вернуться на верх