7

I want to create an API where user can update their profile. In my case, a user can update his/her username and password. To change his/her profile, an API link should be /api/change/usernameOfThatUser. When I use a non-existing username in the link, I still get the userProfileChange API page, and the input boxes are not filled with previous data. How can I solve this?

serializers.py

User = get_user_model()

class UserProfileChangeSerializer(ModelSerializer):
    username = CharField(required=False, allow_blank=True, initial="current username")
    class Meta:
        model = User
        fields = [
            'username',
            'password',
        ]

    def update(self, instance, validated_data):
        instance.username = validated_data.get('username',instance.username)
        print('instance of username',instance.username)
        return instance 

views.py

class UserProfileChangeAPIView(UpdateAPIView):
    serializer_class = UserProfileChangeSerializer
    lookup_field = 'username'

urls.py

  url(r'^change/(?P<username>[\w-]+)$', UserProfileChangeAPIView.as_view(), name='changeProfile'),
3
  • What you want to happen when you use non existed username in the link? Commented Jul 18, 2016 at 10:55
  • Your question doesn't make sense. "How can i solve this?" << you need to tell us what behavior is expected here because the one you have is the one I'd expect. Commented Jul 18, 2016 at 11:32
  • suppose my username is michael then what i want is if i want to change my username then i would do /api/users/michael and the page will be shown with username field and password field. In username field, my name will be already filled in, i would then edit it and save. Commented Jul 18, 2016 at 11:40

1 Answer 1

10

Maybe try doing something like this instead in your views.py?

from rest_framework import generics, mixins, permissions

User = get_user_model()

class UserIsOwnerOrReadOnly(permissions.BasePermission):
    def has_object_permission(self, request, view, obj):
        if request.method in permissions.SAFE_METHODS:
            return True
        return obj.id == request.user.id

class UserProfileChangeAPIView(generics.RetrieveAPIView,
                               mixins.DestroyModelMixin,
                               mixins.UpdateModelMixin):
    permission_classes = (
        permissions.IsAuthenticated,
        UserIsOwnerOrReadOnly,
    )
    serializer_class = UserProfileChangeSerializer
    parser_classes = (MultiPartParser, FormParser,)

    def get_object(self):
        username = self.kwargs["username"]
        obj = get_object_or_404(User, username=username)
        return obj

    def delete(self, request, *args, **kwargs):
        return self.destroy(request, *args, **kwargs)

    def put(self, request, *args, **kwargs):
        return self.update(request, *args, **kwargs)

This will give you all of the existing data for the user based on the username passed in the url. If the username does not exist, it will raise a 404 error. You can also update or delete the object.

Sign up to request clarification or add additional context in comments.

4 Comments

Password is shown in sha256$24000$ form. How can i show empty box only for password? Any authenticated user can open the profile edit page of other user. So can you enlighten me the concept to solve this?
@pri If you take a look at the code now, it will make sure the user can only edit their own profile. It was a permission change. I would create a separate function for password change functionality. Do you need help with that as well?
@pri You can take a look at this for hashing the password: stackoverflow.com/questions/27586095/…
Thanks I will look at hashing the password.

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.