【问题标题】:Django Rest Access Model Values in Another Model另一个模型中的 Django Rest 访问模型值
【发布时间】:2021-08-02 23:23:09
【问题描述】:

我是 Django 新手,我对 Rest API 有一些问题。我想从项目模型中访问用户模型值。我有这样的用户 JSON:

[
    {
        "id": 15,
        "first_name": "Ebrar",
        "last_name": "Bilgili",
        "university": "Bahçeşehir University",
        "faculty": "Software Engineering",
        "user": 17
    },
]

我也有这样的 JSON 项目:

{
    "id": 4,
    "title": "teammate",
    "city": "istanbul",
    "user": 17,
    "user_profile": 15
}

但我想在 Project JSON 中访问用户名、姓氏、大学和学院值,如下所示:

{
        "id": 4,
        "title": "teammate",
        "city": "istanbul",
        "user": 17,
        "user_profile": {
            "first_name": "Ebrar",
            "last_name": "Bilgili",
            "university": "Bahçeşehir University",
            "faculty": "Software Engineering",
        }
}

我进行了很多研究,但找不到任何解决方案。我搜索了所有想到的方法..希望你能帮助我。谢谢。

我的models.py:

class User(AbstractUser):

    username = models.CharField(max_length=250, unique=True)
    email = models.EmailField(max_length=50, unique=True)
    password = models.CharField(max_length=250)

    USERNAME_FIELD = 'username'
    REQUIRED_FIELDS = ['email']


class UserProfile(models.Model):
    user = models.OneToOneField(User, null=True, on_delete=models.CASCADE)
    first_name = models.CharField(max_length=250)
    last_name = models.CharField(max_length=250)
    university = models.CharField(max_length=250)
    faculty = models.CharField(max_length=250)

    class Meta:
        ordering = ["first_name"]

    def __str__(self):
        return "%s %s" % (self.first_name, self.last_name)


class Project(models.Model):
    user = models.ForeignKey(User, on_delete=models.CASCADE)
    user_profile = models.ForeignKey(
        'UserProfile', related_name='name', on_delete=models.CASCADE)
    title = models.CharField(max_length=200)
    city = models.CharField(max_length=50)

    def __str__(self):
        return self.title

还有我的 serializers.py:

class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = '__all__'
        extra_kwargs = {
            'password': {'write_only': True}
        }

    def create(self, validated_data):
        password = validated_data.pop('password', None)
        instance = self.Meta.model(**validated_data)

        if password is not None:
            instance.set_password(password)
        instance.save()
        return instance


class UserProfileSerializer(serializers.ModelSerializer):
    class Meta:
        model = UserProfile
        fields = '__all__'


class ProjectSerializer(serializers.ModelSerializer):
    class Meta:
        model = Project
        fields = '__all__'

和views.py:

class RegisterView(APIView):
    def post(self, request):
        serializer = UserSerializer(data=request.data)
        serializer.is_valid(raise_exception=True)
        serializer.save()

        return Response(serializer.data)


class LoginView(APIView):
    def post(self, request):
        email = request.data['email']
        password = request.data['password']

        user = User.objects.filter(email=email).first()

        if user is None:
            raise AuthenticationFailed('User not found!')

        if not user.check_password(password):
            raise AuthenticationFailed("Incorrect password!")

        payload = {
            'id': user.id,
            'exp': datetime.datetime.utcnow() + datetime.timedelta(minutes=60),
            'iat': datetime.datetime.utcnow()
        }

        token = jwt.encode(payload, 'secret', algorithm='HS256')

        response = Response()

        response.set_cookie(key='token', value=token, httponly=True)
        response.data = {
            'id': user.id,
            'username': user.username,
            'token': token
        }

        return response


class UserView(APIView):

    def get(self, request):
        token = request.COOKIES.get('token')

        if not token:
            raise AuthenticationFailed('Unauthenticated!')

        try:
            payload = jwt.decode(token, 'secret', algorithms=['HS256'])
        except jwt.ExpiredSignatureError:
            raise AuthenticationFailed('Unautheticated!')

        user = User.objects.filter(id=payload['id']).first()
        serializer = UserSerializer(user)

        return Response(serializer.data)

    class UserProfileView(APIView):
        def post(self, request):
            serializer = UserProfileSerializer(data=request.data)
    
            if serializer.is_valid():
                serializer.save()
                return Response(serializer.data, status=status.HTTP_201_CREATED)
            return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
    
        def put(self, request):
            serializer = UserProfileSerializer(data=request.data)
    
            if serializer.is_valid():
                serializer.save()
                return Response(serializer.data)
            return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
    
        def get(self, request):
            try:
                id = request.query_params['id']
                if id != None:
                    user = UserProfile.objects.get(id=id)
                    serializer = UserProfileSerializer(user)
            except:
                users = UserProfile.objects.all()
                serializer = UserProfileSerializer(users, many=True)
    
            return Response(serializer.data)
    
    
    class ProjectView(APIView):
        def post(self, request):
            serializer = ProjectSerializer(data=request.data)
    
            if serializer.is_valid():
                serializer.save()
                return Response(serializer.data, status=status.HTTP_201_CREATED)
            return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
    
        def get(self, request):
            try:
                id = request.query_params['id']
                if id != None:
                    project = Project.objects.get(id=id)
                    serializer = ProjectSerializer(project)
            except:
                projects = Project.objects.all()
                serializer = ProjectSerializer(projects, many=True)
    
            return Response(serializer.data)

【问题讨论】:

  • 可以分享一下model.py和serializer.py吗?
  • 我添加了@SırrıKırımlıoğlu
  • 好的,这些看起来不错。如果你也分享views.py,我想我可以给你你需要的答案。
  • 我添加了它。它有点长.. @SırrıKırımlıoğlu
  • 好的,谢谢。对不起,我其实不需要你的views.py,现在才注意到。我发布了一个答案。试试看,然后告诉我。

标签: python django django-rest-framework nosql rest


【解决方案1】:

试试这个:

class ProjectSerializer(serializers.ModelSerializer):
user_profile = UserProfileSerializer()

class Meta:
    model = Project
    fields = '__all__'

【讨论】:

  • 谢谢!有效!。但我有一些想法。当我想发布新项目时,我可以发布带有用户 ID 的用户模型值还是应该将所有值一一添加?
  • 不明白你的意思。我会伸出援手,这样我们就可以说母语了。
猜你喜欢
  • 1970-01-01
  • 2019-09-30
  • 2021-05-29
  • 1970-01-01
  • 2017-04-17
  • 1970-01-01
  • 2013-06-12
  • 2023-01-03
  • 1970-01-01
相关资源
最近更新 更多