Search code examples
reactjsdjangosession-cookiessessionidcsrf-token

React, Django: How do I manage a session after a user changes their password?


I am developing an administration panel in React with Django for user management, amongst other actions.

Django takes care of ORM and users' login.
When the user first logs in, the React app obtains the session id and the csrf token. The app asks for the csrf token from the document cookies and that's the token used for later REST queries.

Issue/Challenge:
One of the app component allows a user to change the password.
However, after a successful password change doing so, the session id and the csrf token become expired and the REST queries I do from that time on are unauthorized.

If I reload the page, after then, the session is expired. I tried to get the token again but it doesn't work.

Question:

  • How can I update the session id after changing the password?
  • Should I just send the user outside the app for them to log in again?

I don't know if that is the common way to proceded.

Below is the function that I use to get the token:

getCookie(name) {
    console.log(name);

    let cookieValue = null;
    if (document.cookie && document.cookie !== '') {
      const cookies = document.cookie.split(';');
      for (let i = 0; i < cookies.length; i += 1) {
        const cookie = jQuery.trim(cookies[i]);
        // Does this cookie string begin with the name we want?
        if (cookie.substring(0, name.length + 1) === (`${name}=`)) {
          cookieValue = decodeURIComponent(cookie.substring(name.length + 1));
          break;
        }
      }
    }
    console.log(cookieValue);
    this.setState({
      token: cookieValue,
    });

//getCookie('csrftoken')

I don't usually work with cookies, apart from getting the csrf token, so I would appreciate any help.

Update

I found the problem might be due to Django: https://docs.djangoproject.com/en/3.1/topics/auth/default/#session-invalidation-on-password-change

As I am changing the password with Django Rest Framework -- following this tutorial: https://medium.com/django-rest/django-rest-framework-change-password-and-update-profile-1db0c144c0a3 -- I used the function update_session_auth_hash in the serializer as follows:

## serializer
    def update(self, instance, validated_data):
        instance.set_password(validated_data['password'])
        instance.save()

        request = self.context['request']
        user = request.user
        update_session_auth_hash(request, user)
             
        return instance

I doesn't work either...


Solution

  • I finally managed to make it work by using instance instead of user:

    ## serializer
        def update(self, instance, validated_data):
            instance.set_password(validated_data['password'])
            instance.save()
    
            request = self.context['request']
            update_session_auth_hash(request, instance)
                 
            return instance