Ejemplo n.º 1
0
    def test_override_configs(self):
        self.app.config['JWT_TOKEN_LOCATION'] = 'cookies'
        self.app.config['JWT_HEADER_NAME'] = 'Auth'
        self.app.config['JWT_HEADER_TYPE'] = 'JWT'

        self.app.config['JWT_COOKIE_SECURE'] = True
        self.app.config['JWT_ACCESS_COOKIE_NAME'] = 'banana1'
        self.app.config['JWT_REFRESH_COOKIE_NAME'] = 'banana2'
        self.app.config['JWT_ACCESS_COOKIE_PATH'] = '/banana/'
        self.app.config['JWT_REFRESH_COOKIE_PATH'] = '/banana2/'
        self.app.config['JWT_COOKIE_CSRF_PROTECT'] = False
        self.app.config['JWT_ACCESS_CSRF_COOKIE_NAME'] = 'banana1a'
        self.app.config['JWT_REFRESH_CSRF_COOKIE_NAME'] = 'banana2a'
        self.app.config['JWT_CSRF_HEADER_NAME'] = 'bananaaaa'

        self.app.config['JWT_ACCESS_TOKEN_EXPIRES'] = timedelta(minutes=5)
        self.app.config['JWT_REFRESH_TOKEN_EXPIRES'] = timedelta(days=7)
        self.app.config['JWT_ALGORITHM'] = 'HS512'
        self.app.config['JWT_BLACKLIST_ENABLED'] = True
        self.app.config['JWT_BLACKLIST_STORE'] = simplekv.memory.DictStore()
        self.app.config['JWT_BLACKLIST_TOKEN_CHECKS'] = 'all'

        with self.app.test_request_context():
            self.assertEqual(get_token_location(), 'cookies')
            self.assertEqual(get_jwt_header_name(), 'Auth')
            self.assertEqual(get_jwt_header_type(), 'JWT')

            self.assertEqual(get_cookie_secure(), True)
            self.assertEqual(get_access_cookie_name(), 'banana1')
            self.assertEqual(get_refresh_cookie_name(), 'banana2')
            self.assertEqual(get_access_cookie_path(), '/banana/')
            self.assertEqual(get_refresh_cookie_path(), '/banana2/')
            self.assertEqual(get_cookie_csrf_protect(), False)
            self.assertEqual(get_access_csrf_cookie_name(), 'banana1a')
            self.assertEqual(get_refresh_csrf_cookie_name(), 'banana2a')
            self.assertEqual(get_csrf_header_name(), 'bananaaaa')

            self.assertEqual(get_access_expires(), timedelta(minutes=5))
            self.assertEqual(get_refresh_expires(), timedelta(days=7))
            self.assertEqual(get_algorithm(), 'HS512')
            self.assertEqual(get_blacklist_enabled(), True)
            self.assertIsInstance(get_blacklist_store(),
                                  simplekv.memory.DictStore)
            self.assertEqual(get_blacklist_checks(), 'all')

        self.app.config['JWT_TOKEN_LOCATION'] = 'banana'
        self.app.config['JWT_HEADER_NAME'] = ''
        self.app.config['JWT_ACCESS_TOKEN_EXPIRES'] = 'banana'
        self.app.config['JWT_REFRESH_TOKEN_EXPIRES'] = 'banana'

        self.app.testing = True  # Propagate exceptions
        with self.app.test_request_context():
            with self.assertRaises(RuntimeError):
                get_jwt_header_name()
            with self.assertRaises(RuntimeError):
                get_access_expires()
            with self.assertRaises(RuntimeError):
                get_refresh_expires()
            with self.assertRaises(RuntimeError):
                get_token_location()
Ejemplo n.º 2
0
def _encode_refresh_token(identity, secret, algorithm, token_expire_delta):
    """
    Creates a new refresh token, which can be used to create subsequent access
    tokens.

    :param identity: Some identifier used to identify the owner of this token
    :param secret: Secret key to encode the JWT with
    :param algorithm: Which algorithm to use for the toek
    :return: Encoded JWT
    """
    now = datetime.datetime.utcnow()
    uid = str(uuid.uuid4())
    token_data = {
        'exp': now + token_expire_delta,
        'iat': now,
        'nbf': now,
        'jti': uid,
        'identity': identity,
        'type': 'refresh',
    }
    if get_token_location() == 'cookies' and get_cookie_csrf_protect():
        token_data['csrf'] = _create_csrf_token()
    encoded_token = jwt.encode(token_data, secret, algorithm).decode('utf-8')

    # If blacklisting is enabled, store this token in our key-value store
    blacklist_enabled = get_blacklist_enabled()
    if blacklist_enabled:
        store_token(token_data, revoked=False)
    return encoded_token
Ejemplo n.º 3
0
def _decode_jwt(token, secret, algorithm):
    """
    Decodes an encoded JWT

    :param token: The encoded JWT string to decode
    :param secret: Secret key used to encode the JWT
    :param algorithm: Algorithm used to encode the JWT
    :return: Dictionary containing contents of the JWT
    """
    # ext, iat, and nbf are all verified by pyjwt. We just need to make sure
    # that the custom claims we put in the token are present
    data = jwt.decode(token, secret, algorithm=algorithm)
    if 'jti' not in data or not isinstance(data['jti'], six.string_types):
        raise JWTDecodeError("Missing or invalid claim: jti")
    if 'identity' not in data:
        raise JWTDecodeError("Missing claim: identity")
    if 'type' not in data or data['type'] not in ('refresh', 'access'):
        raise JWTDecodeError("Missing or invalid claim: type")
    if data['type'] == 'access':
        if 'fresh' not in data or not isinstance(data['fresh'], bool):
            raise JWTDecodeError("Missing or invalid claim: fresh")
        if 'user_claims' not in data or not isinstance(data['user_claims'],
                                                       dict):
            raise JWTDecodeError("Missing or invalid claim: user_claims")
    if get_token_location() == 'cookies' and get_cookie_csrf_protect():
        if 'csrf' not in data or not isinstance(data['csrf'],
                                                six.string_types):
            raise JWTDecodeError("Missing or invalid claim: csrf")
    return data
Ejemplo n.º 4
0
def _encode_access_token(identity, secret, algorithm, token_expire_delta,
                         fresh, user_claims):
    """
    Creates a new access token.

    :param identity: Some identifier of who this client is (most common would be a client id)
    :param secret: Secret key to encode the JWT with
    :param fresh: If this should be a 'fresh' token or not
    :param algorithm: Which algorithm to use for the toek
    :return: Encoded JWT
    """
    # Verify that all of our custom data we are encoding is what we expect
    if not isinstance(user_claims, dict):
        raise JWTEncodeError('user_claims must be a dict')
    if not isinstance(fresh, bool):
        raise JWTEncodeError('fresh must be a bool')
    try:
        json.dumps(user_claims)
    except Exception as e:
        raise JWTEncodeError('Error json serializing user_claims: {}'.format(
            str(e)))

    # Create the jwt
    now = datetime.datetime.utcnow()
    uid = str(uuid.uuid4())
    token_data = {
        'exp': now + token_expire_delta,
        'iat': now,
        'nbf': now,
        'jti': uid,
        'identity': identity,
        'fresh': fresh,
        'type': 'access',
        'user_claims': user_claims,
    }
    if get_token_location() == 'cookies' and get_cookie_csrf_protect():
        token_data['csrf'] = _create_csrf_token()
    encoded_token = jwt.encode(token_data, secret, algorithm).decode('utf-8')

    # If blacklisting is enabled and configured to store access and refresh tokens,
    # add this token to the store
    blacklist_enabled = get_blacklist_enabled()
    if blacklist_enabled and get_blacklist_checks() == 'all':
        store_token(token_data, revoked=False)
    return encoded_token
Ejemplo n.º 5
0
def _decode_jwt_from_request(type):
    token_locations = get_token_location()

    # JWT can be in either headers or cookies
    if 'headers' in token_locations and 'cookies' in token_locations:
        try:
            return _decode_jwt_from_headers()
        except NoAuthorizationError:
            pass
        try:
            return _decode_jwt_from_cookies(type)
        except NoAuthorizationError:
            pass
        raise NoAuthorizationError("Missing JWT in header and cookies")

    # JWT can only be in headers
    elif 'headers' in token_locations:
        return _decode_jwt_from_headers()

    # JWT can only be in cookie
    else:
        return _decode_jwt_from_cookies(type)
Ejemplo n.º 6
0
    def test_default_configs(self):
        with self.app.test_request_context():
            self.assertEqual(get_token_location(), 'headers')
            self.assertEqual(get_jwt_header_name(), 'Authorization')
            self.assertEqual(get_jwt_header_type(), 'Bearer')

            self.assertEqual(get_cookie_secure(), False)
            self.assertEqual(get_access_cookie_name(), 'access_token_cookie')
            self.assertEqual(get_refresh_cookie_name(), 'refresh_token_cookie')
            self.assertEqual(get_access_cookie_path(), None)
            self.assertEqual(get_refresh_cookie_path(), None)
            self.assertEqual(get_cookie_csrf_protect(), True)
            self.assertEqual(get_access_csrf_cookie_name(),
                             'csrf_access_token')
            self.assertEqual(get_refresh_csrf_cookie_name(),
                             'csrf_refresh_token')
            self.assertEqual(get_csrf_header_name(), 'X-CSRF-TOKEN')

            self.assertEqual(get_access_expires(), timedelta(minutes=15))
            self.assertEqual(get_refresh_expires(), timedelta(days=30))
            self.assertEqual(get_algorithm(), 'HS256')
            self.assertEqual(get_blacklist_enabled(), False)
            self.assertEqual(get_blacklist_store(), None)
            self.assertEqual(get_blacklist_checks(), 'refresh')
Ejemplo n.º 7
0
def _decode_jwt_from_request(type):
    token_location = get_token_location()
    if token_location == 'headers':
        return _decode_jwt_from_headers()
    else:
        return _decode_jwt_from_cookies(type)