예제 #1
0
    def post(self, request, format=None):
        #  check token refresh valid
        serializer = TokenRefreshSerializer(data=request.data)
        try:
            serializer.is_valid(raise_exception=True)
        except TokenError as e:
            raise InvalidToken(e.args[0])

        response = Response()
        """ send http only cookies """
        data = serializer._validated_data

        payload = {"access": data["access"], "refresh": data["refresh"]}
        tomorrow = datetime.now() + datetime.timedelta(days=1)
        expires = datetime.strftime(tomorrow, "%a, %d-%b-%Y %H:%M:%S GMT")
        response.set_cookie(
            key=settings.SIMPLE_JWT["AUTH_COOKIE"],
            value=data["access"],
            expires=expires,
            secure=settings.SIMPLE_JWT["AUTH_COOKIE_SECURE"],
            httponly=settings.SIMPLE_JWT["AUTH_COOKIE_HTTP_ONLY"],
            samesite=settings.SIMPLE_JWT["AUTH_COOKIE_SAMESITE"],
        )
        response.data = {"Messege": "refresh Success", "data": payload}
        response.status_code = status.HTTP_200_OK
        return response
예제 #2
0
def refresh_token(request: Request) -> JsonResponse:
    """
    Refreshes a user's token info. They should contain:
     - Access token
     - Refresh token
     - Spotify access token (optional)
     - Spotify refresh token (if spotify access token is provided).
    """
    if settings.DEBUG:
        print(json.loads(request.body))
    # Refresh user's token
    body = json.loads(request.body)
    spotify_params = {}
    spotify_params['access_token'] = body.pop('spotify_access_token', '')
    spotify_params['refresh_token'] = body.pop('spotify_refresh_token', '')
    try:
        ser = TokenRefreshSerializer(data=body)
        ser.is_valid()
    except TokenError:
        # Request is not valid.
        return JsonResponse({'error': 'Refresh Token is Invalid'},
                            status=status.HTTP_401_UNAUTHORIZED)

    if settings.DEBUG:
        print('validated', ser.validated_data)
    # If this user's credentials doesn't contain spotify credentials, just return it.
    if not spotify_params['access_token'] or not spotify_params[
            'refresh_token']:
        return JsonResponse(ser.validated_data)

    # Check and refresh user's spotify token
    try:
        response = refresh_token_info(spotify_params)
        print(response)
        return JsonResponse({
            'access_token': ser.validated_data['access'],
            'refresh': body['refresh'],
            'spotify_access_token': response['access_token'],
            'spotify_refresh_token': response['refresh_token']
        })
    except pyrequests.RequestException:
        pass
    try:
        refresh_response = refresh_token_info(spotify_params)
        spotify_params['access_token'] = refresh_response['access_token']
        spotify_params['refresh_token'] = refresh_response['refresh_token']
        return JsonResponse({
            'access_token':
            ser.validated_data['access'],
            'refresh':
            body['refresh'],
            'spotify_access_token':
            spotify_params['access_token'],
            'spotify_refresh_token':
            spotify_params['refresh_token']
        })
    except pyrequests.RequestException:
        return JsonResponse({'error': 'Refresh Token is Invalid'},
                            status=status.HTTP_401_UNAUTHORIZED)
예제 #3
0
    def get_access_token_from_refresh_token(self,request):
        
        serializer = TokenRefreshSerializer(data = request.data)
        try:
            serializer.is_valid(raise_exception=True)
        except TokenError as e:
            raise InvalidToken(e.args[0])

        return Response(serializer.validated_data,status = status.HTTP_200_OK)
예제 #4
0
def token_refresh_handler(refresh):
    """
    Takes a refresh type JSON web token and returns an access type JSON web
    token if the refresh token is valid.
    """
    ser = TokenRefreshSerializer(data={'refresh': refresh})
    ser.is_valid(raise_exception=True)
    res = dict(refresh=ser.validated_data.get('refresh'),
               access=ser.validated_data.get('access'))
    return res
예제 #5
0
    def refresh(self, request):
        serializer = TokenRefreshSerializer(data=request.data,
                                            context={'request': request})

        try:
            serializer.is_valid(raise_exception=True)
        except TokenError as e:
            raise InvalidToken(e.args[0])

        return Response(serializer.validated_data, status=status.HTTP_200_OK)
예제 #6
0
    def test_it_should_raise_token_error_if_token_has_wrong_type(self):
        token = RefreshToken()
        token[api_settings.TOKEN_TYPE_CLAIM] = 'wrong_type'

        s = TokenRefreshSerializer(data={'refresh': str(token)})

        with self.assertRaises(TokenError) as e:
            s.is_valid()

        self.assertIn("wrong type", e.exception.args[0])
예제 #7
0
    def decorated_function(self, request, *args, **kwargs):
        self.headers = {'Authorization': request.META['HTTP_AUTHORIZATION']}
        if 'headers' in request.META and 'refresh' in request.META['headers']:
            raw_token = request.META['headers']['refresh'].split(" ")[-1]

            token_serializer = TokenRefreshSerializer(data={'refresh': raw_token})
            token_serializer.is_valid(raise_exception=True)
            access = token_serializer.validated_data['access']
            refresh = token_serializer.validated_data['refresh']

            self.headers['Refresh'] = settings.JWT_HEADER_TYPE + refresh
            self.headers['Authorization'] = settings.JWT_HEADER_TYPE + access

        return func(self, request, *args, **kwargs)
    def test_it_should_not_validate_if_token_invalid(self):
        token = RefreshToken()
        del token['exp']

        s = TokenRefreshSerializer(data={'refresh': str(token)})
        self.assertFalse(s.is_valid())
        self.assertIn('non_field_errors', s.errors)
        self.assertIn("has no 'exp' claim", s.errors['non_field_errors'][0])

        token.set_exp(lifetime=-timedelta(days=1))

        s = TokenRefreshSerializer(data={'refresh': str(token)})
        self.assertFalse(s.is_valid())
        self.assertIn('non_field_errors', s.errors)
        self.assertIn('invalid or expired', s.errors['non_field_errors'][0])
예제 #9
0
    def post(self, request):
        """
        API -> POST /api/v1/user/refresh/token/
        """

        serializer = TokenRefreshSerializer(data=request.data)
        try:
            if serializer.is_valid():
                token_service = TokenService()
                user_id = token_service.get_user_from_token(
                    request.data['refresh'])

                if user_id is None:
                    return Response({'error': 'Invalid Claims'},
                                    status=status.HTTP_401_UNAUTHORIZED)

                try:
                    User.objects.get(id=user_id, is_deleted=False)
                except ObjectDoesNotExist:
                    return Response({'error': 'User does not exist'},
                                    status=status.HTTP_401_UNAUTHORIZED)

                tokens = serializer.validated_data

                return Response(
                    {
                        'access_token': tokens['access'],
                        'refresh_token': tokens['refresh']
                    },
                    status=status.HTTP_200_OK)
        except Exception as error:
            return Response({'error': str(error)},
                            status=status.HTTP_403_FORBIDDEN)
예제 #10
0
    def test_it_should_return_refresh_token_if_tokens_should_be_rotated(self):
        refresh = RefreshToken()

        refresh['test_claim'] = 'arst'

        old_jti = refresh['jti']
        old_exp = refresh['exp']

        # Serializer validates
        ser = TokenRefreshSerializer(data={'refresh': str(refresh)})

        now = aware_utcnow() - api_settings.ACCESS_TOKEN_LIFETIME / 2

        with override_api_settings(ROTATE_REFRESH_TOKENS=True, BLACKLIST_AFTER_ROTATION=False):
            with patch('rest_framework_simplejwt.tokens.aware_utcnow') as fake_aware_utcnow:
                fake_aware_utcnow.return_value = now
                self.assertTrue(ser.is_valid())

        access = AccessToken(ser.validated_data['access'])
        new_refresh = RefreshToken(ser.validated_data['refresh'])

        self.assertEqual(refresh['test_claim'], access['test_claim'])
        self.assertEqual(refresh['test_claim'], new_refresh['test_claim'])

        self.assertNotEqual(old_jti, new_refresh['jti'])
        self.assertNotEqual(old_exp, new_refresh['exp'])

        self.assertEqual(access['exp'], datetime_to_epoch(now + api_settings.ACCESS_TOKEN_LIFETIME))
        self.assertEqual(new_refresh['exp'], datetime_to_epoch(now + api_settings.REFRESH_TOKEN_LIFETIME))
    def test_it_should_not_validate_if_token_has_wrong_type(self):
        token = RefreshToken()
        token[api_settings.TOKEN_TYPE_CLAIM] = 'wrong_type'

        s = TokenRefreshSerializer(data={'refresh': str(token)})
        self.assertFalse(s.is_valid())
        self.assertIn('non_field_errors', s.errors)
        self.assertIn("wrong type", s.errors['non_field_errors'][0])
예제 #12
0
    def process_template_response(self, request, response):
        try:
            access_token = request.COOKIES[settings.SIMPLE_JWT["AUTH_COOKIE"]]
            refesh_token = request.COOKIES[
                settings.SIMPLE_JWT["AUTH_COOKIE_REF"]]
            # check if the access token is valid
            # if not, send new access token to cookie
            if access_token:
                key = settings.SECRET_KEY
            else:
                return response
            try:
                decoded_access_token = jwt.decode(access_token,
                                                  key,
                                                  algorithms=["HS256"])
                return response
            except jwt.ExpiredSignatureError:
                serializer = TokenRefreshSerializer(
                    data={"refresh": refesh_token})
                try:
                    serializer.is_valid(raise_exception=True)
                except TokenError as e:
                    # Code that is executed in each request after the view is
                    return response
                """ send http only cookies """
                data = serializer._validated_data

                response.set_cookie(
                    key=settings.SIMPLE_JWT["AUTH_COOKIE"],
                    value=data["access"],
                    expires=settings.SIMPLE_JWT["ACCESS_TOKEN_LIFETIME"],
                    secure=settings.SIMPLE_JWT["AUTH_COOKIE_SECURE"],
                    httponly=settings.SIMPLE_JWT["AUTH_COOKIE_HTTP_ONLY"],
                    samesite=settings.SIMPLE_JWT["AUTH_COOKIE_SAMESITE"],
                )
                response.set_cookie(
                    key=settings.SIMPLE_JWT["AUTH_COOKIE_REF"],
                    value=data["refresh"],
                    expires=settings.SIMPLE_JWT["REFRESH_TOKEN_LIFETIME"],
                    secure=settings.SIMPLE_JWT["AUTH_COOKIE_SECURE"],
                    httponly=settings.SIMPLE_JWT["AUTH_COOKIE_HTTP_ONLY"],
                    samesite=settings.SIMPLE_JWT["AUTH_COOKIE_SAMESITE"],
                )
                return response
        except KeyError:
            return response
예제 #13
0
파일: views.py 프로젝트: hxt365/Safety
    def post(self, request, *args, **kwargs):
        data = {
            'refresh': cookies.get_cookie(request=request, key='refresh_token')
        }
        serializer = TokenRefreshSerializer(data=data)

        try:
            serializer.is_valid(raise_exception=True)
        except Exception:
            return Response(data={'message': 'refresh token not found'},
                            status=status.HTTP_403_FORBIDDEN)

        access_token = serializer.validated_data['access']
        response = Response(data={'message': 'refreshed token successfully'},
                            status=status.HTTP_200_OK)
        response = auths.helpers.set_cookies_with_access_token(
            response=response, access_token=access_token)
        return response
예제 #14
0
파일: api.py 프로젝트: diegorocha/boticario
 def refresh_token(self, request):
     serializer = TokenRefreshSerializer(data=request.data)
     try:
         if not serializer.is_valid():
             return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
         return Response(serializer.validated_data, status=status.HTTP_200_OK)
     except TokenError as ex:
         logger.exception(ex)
         return Response({"refresh": ["Token inválido"]}, status=status.HTTP_400_BAD_REQUEST)
예제 #15
0
    def test_it_should_raise_token_error_if_token_invalid(self):
        token = RefreshToken()
        del token['exp']

        s = TokenRefreshSerializer(data={'refresh': str(token)})

        with self.assertRaises(TokenError) as e:
            s.is_valid()

        self.assertIn("has no 'exp' claim", e.exception.args[0])

        token.set_exp(lifetime=-timedelta(days=1))

        s = TokenRefreshSerializer(data={'refresh': str(token)})

        with self.assertRaises(TokenError) as e:
            s.is_valid()

        self.assertIn('invalid or expired', e.exception.args[0])
예제 #16
0
    def test_it_should_return_access_token_if_everything_ok(self):
        refresh = RefreshToken()
        refresh['test_claim'] = 'arst'

        # Serializer validates
        s = TokenRefreshSerializer(data={'refresh': str(refresh)})

        now = aware_utcnow() - api_settings.ACCESS_TOKEN_LIFETIME / 2

        with patch('rest_framework_simplejwt.tokens.aware_utcnow') as fake_aware_utcnow:
            fake_aware_utcnow.return_value = now
            self.assertTrue(s.is_valid())

        access = AccessToken(s.validated_data['access'])

        self.assertEqual(refresh['test_claim'], access['test_claim'])
        self.assertEqual(access['exp'], datetime_to_epoch(now + api_settings.ACCESS_TOKEN_LIFETIME))
예제 #17
0
    def test_it_should_blacklist_refresh_token_if_tokens_should_be_rotated_and_blacklisted(
        self, ):
        self.assertEqual(OutstandingToken.objects.count(), 0)
        self.assertEqual(BlacklistedToken.objects.count(), 0)

        refresh = RefreshToken()

        refresh["test_claim"] = "arst"

        old_jti = refresh["jti"]
        old_exp = refresh["exp"]

        # Serializer validates
        ser = TokenRefreshSerializer(data={"refresh": str(refresh)})

        now = aware_utcnow() - api_settings.ACCESS_TOKEN_LIFETIME / 2

        with override_api_settings(ROTATE_REFRESH_TOKENS=True,
                                   BLACKLIST_AFTER_ROTATION=True):
            with patch("rest_framework_simplejwt.tokens.aware_utcnow"
                       ) as fake_aware_utcnow:
                fake_aware_utcnow.return_value = now
                self.assertTrue(ser.is_valid())

        access = AccessToken(ser.validated_data["access"])
        new_refresh = RefreshToken(ser.validated_data["refresh"])

        self.assertEqual(refresh["test_claim"], access["test_claim"])
        self.assertEqual(refresh["test_claim"], new_refresh["test_claim"])

        self.assertNotEqual(old_jti, new_refresh["jti"])
        self.assertNotEqual(old_exp, new_refresh["exp"])

        self.assertEqual(
            access["exp"],
            datetime_to_epoch(now + api_settings.ACCESS_TOKEN_LIFETIME))
        self.assertEqual(
            new_refresh["exp"],
            datetime_to_epoch(now + api_settings.REFRESH_TOKEN_LIFETIME),
        )

        self.assertEqual(OutstandingToken.objects.count(), 1)
        self.assertEqual(BlacklistedToken.objects.count(), 1)

        # Assert old refresh token is blacklisted
        self.assertEqual(BlacklistedToken.objects.first().token.jti, old_jti)
def resolve_refresh_token(_, info, token):
    data = {"refresh": token}
    serializer = TokenRefreshSerializer(data=data)
    if serializer.is_valid():
        return serializer.validated_data