3

My users/models.py file looks as below.

class User(AbstractUser):
    is_customer = models.BooleanField(default=False)
    is_courier = models.BooleanField(default=False)
    is_merchant = models.BooleanField(default=False)


class Profile(models.Model):
    contact_number = models.CharField(max_length=10, unique=True)
    rating = models.IntegerField(blank=True)
    created = models.DateTimeField(auto_now_add=True)
    updated = models.DateTimeField(auto_now=True)

    user = models.ForeignKey(User, on_delete=models.CASCADE)

My current users/serializers.py looks like below.

class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = '__all__'

My users/api.py looks like below.

class UserViewSet(viewsets.ModelViewSet):
    queryset = User.objects.all()
    permission_classes = [
        permissions.AllowAny
    ]
    serializer_class = UserSerializer

My users/urls.py has the below:

router.register('api/users', UserViewSet, 'users')

My current setup works well with the UserViewSet. http://127.0.0.1:8000/api/users/ displays all the users and http://127.0.0.1:8000/api/users/1/ displays the user according to the ID.

My question is, How can I load up the user profile when I goto the below the URL http://127.0.0.1:8000/api/users/1/profile

Any help is much appreciated. Thank you in advance.

2 Answers 2

3

Create a new serializer for Profile model

class ProfileSerializer(serializers.ModelSerializer):
    class Meta:
        model = Profile
        fields = "__all__"

then create a new view class for the Profile.

from rest_framework.views import APIView
from rest_framework.response import Response
from django.shortcuts import get_object_or_404


class ProfileAPI(APIView):
    def get(self, request, *args, **kwargs):
        user = get_object_or_404(User, pk=kwargs['user_id'])
        profile_serializer = ProfileSerializer(user.profile)
        return Response(profile_serializer.data)

Then, wire up the view in urls.py

urlpatterns = [
    # your other url configs
    path('api/users/<user_id>/profile/', ProfileAPI.as_view())
]

Update-1

Implementation using ViewSet class

from rest_framework import viewsets
from rest_framework.response import Response
from django.shortcuts import get_object_or_404


class ProfileAPI(viewsets.ViewSet):
    def get(self, request, *args, **kwargs):
        user = get_object_or_404(User, pk=kwargs['user_id'])
        profile_serializer = ProfileSerializer(user.profile)
        return Response(profile_serializer.data)

Update-2

from rest_framework import viewsets


class ProfileAPI(viewsets.ModelViewSet):
    serializer_class = ProfileSerializer

    def get_queryset(self):
        return Profile.objects.filter(user=self.kwargs['user_id'])

and in your urls.py register the viewset as

router.register('api/users/(?P<user_id>\d+)/profile', ProfileAPI, base_name='profile_api')
Sign up to request clarification or add additional context in comments.

8 Comments

Thank JPG. This works. Is there a way that I can use rest_framework's viewsets to implement this rather than using the APIView?
APIView also belongs to DRF and I think viewsets classes are not required here since you are only dealing with the HTTP GET request
@NadunPerera Anyway, I've updated my answer. Hope it helps. and don't forget to mark and vote the answer :)
How would you register the URL for the viewset above in the urls.py?
you don't need to register it....as I said, it's only dealing with HTTP GET request
|
0

i have used **AbstractUser ** and **custom user manager ** i have used ViewSets.ViewSet along with Model Serializers

#urls.py file#

from django.urls import path, include
from rest_framework.routers import DefaultRouter
from .views import ProfileViewSet, LoginViewSet, RegisterViewSet

router = DefaultRouter()
router.register(r'register', RegisterViewSet, basename='register')
router.register(r'login', LoginViewSet, basename='login')
router.register(r'profile', ProfileViewSet, basename='profile')

urlpatterns = [
path('', include(router.urls)),
]

#views.py file#

from rest_framework.response import Response
from rest_framework.viewsets import ViewSet
from .models import user_reg
from .serializers import RegisterSerializer


class ProfileViewSet(ViewSet):

    def partial_update(self, request, pk=None):    #partially update the profile

        try:
            user_detail = user_reg.objects.get(pk=pk)
           
            serializer = RegisterSerializer(user_detail,data=request.data, partial=True)

            if not serializer.is_valid():
                return Response({'data':'internal server error','message':'error aa gyi'},500)

            serializer.save()

        except Exception as e:

            return Response('some exception occured' + str(e))

        return Response('record Updated successfully')

    def retrieve(self,request, pk=None):    #get or retrieve the profile from database

        queryset = user_reg.objects.get(pk=pk)
    
        serializer_class = RegisterSerializer(queryset)
    
        return Response(serializer_class.data)

#serializer.py file#

from rest_framework import serializers
from .models import user_reg

class RegisterSerializer(serializers.ModelSerializer):

    class Meta:
        model = user_reg
        fields = ('username','first_name','last_name','email')  #custom fields i made 
                                                                 u can change this

#models.py#

from django.db import models
from django.contrib.auth.models import AbstractUser
from django.contrib.auth.models import UserManager



class user_reg(AbstractUser):
    mobile = models.CharField(max_length=10, blank=True, null=True)
    age = models.IntegerField(null=True,blank=False)
    gender = models.CharField(max_length= 8,blank=True)
    objects = UserManager()

    class Meta:
        verbose_name='user'

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.