def login(): # lookup user from username/email try: username = request.json.get('username', None) or request.json['email'] password = request.json['password'] except KeyError: raise ApiError("must supply 'username' and 'password'", 401) user = User.check_credentials(username, password) if not user: raise ApiError('Invalid username or password', 401) # if email verification is enforced, deny login and send email if current_app.config['EMAIL_VERIFICATION'] and not user.email_verified: user.send_confirmation() raise ApiError('email not verified', 401) # check allowed domain if not_authorized('ALLOWED_EMAIL_DOMAINS', groups=[user.domain]): raise ApiError('unauthorized domain', 403) # assign customers customers = get_customers(user.email, groups=[user.domain]) # generate token token = create_token(user.id, user.name, user.email, provider='basic', customers=customers, roles=user.roles, email=user.email, email_verified=user.email_verified) return jsonify(token=token.tokenize)
def login(): # lookup user from username/email try: username = request.json.get('username', None) or request.json['email'] password = request.json['password'] except KeyError: raise ApiError("must supply 'username' and 'password'", 401) user = User.check_credentials(username, password) if not user: raise ApiError('Invalid username or password', 401) # if email verification is enforced, deny login and send email if current_app.config['EMAIL_VERIFICATION'] and not user.email_verified: user.send_confirmation() raise ApiError('email not verified', 403) # check allowed domain if not_authorized('ALLOWED_EMAIL_DOMAINS', groups=[user.domain]): raise ApiError('unauthorized domain', 403) # check user is active & update last login if user.status != 'active': raise ApiError('User {} not active'.format(user.login), 403) user.update_last_login() groups = [g.name for g in user.get_groups()] scopes = Permission.lookup(login=user.login, roles=user.roles + groups) customers = get_customers(login=user.login, groups=[user.domain] + groups) auth_audit_trail.send(current_app._get_current_object(), event='basic-auth-login', message='user login via BasicAuth', user=user.login, customers=customers, scopes=scopes, roles=user.roles, groups=groups, resource_id=user.id, type='user', request=request) # generate token token = create_token(user_id=user.id, name=user.name, login=user.login, provider='basic', customers=customers, scopes=scopes, roles=user.roles, groups=groups, email=user.email, email_verified=user.email_verified) return jsonify(token=token.tokenize)
def login(): # lookup user from username/email try: username = request.json.get('username', None) or request.json['email'] password = request.json['password'] except KeyError: raise ApiError("must supply 'username' and 'password'", 401) user = User.check_credentials(username, password) if not user: raise ApiError('Invalid username or password', 401) # if email verification is enforced, deny login and send email if current_app.config['EMAIL_VERIFICATION'] and not user.email_verified: user.send_confirmation() raise ApiError('email not verified', 403) # check allowed domain if not_authorized('ALLOWED_EMAIL_DOMAINS', groups=[user.domain]): raise ApiError('unauthorized domain', 403) # check user is active & update last login if user.status != 'active': raise ApiError('User {} not active'.format(user.login), 403) user.update_last_login() groups = [g.name for g in user.get_groups()] scopes = Permission.lookup(login=user.login, roles=user.roles + groups) customers = get_customers(login=user.login, groups=[user.domain] + groups) auth_audit_trail.send(current_app._get_current_object(), event='basic-auth-login', message='user login via BasicAuth', user=user.login, customers=customers, scopes=scopes, resource_id=user.id, type='user', request=request) # generate token token = create_token(user_id=user.id, name=user.name, login=user.login, provider='basic', customers=customers, scopes=scopes, roles=user.roles, groups=groups, email=user.email, email_verified=user.email_verified) return jsonify(token=token.tokenize)
def wrapped(*args, **kwargs): # API Key (Authorization: Key <key>) if 'Authorization' in request.headers: auth_header = request.headers['Authorization'] m = re.match(r'Key (\S+)', auth_header) key = m.group(1) if m else None # API Key (X-API-Key: <key>) elif 'X-API-Key' in request.headers: key = request.headers['X-API-Key'] # API Key (/foo?api-key=<key>) else: key = request.args.get('api-key', None) if key: key_info = ApiKey.verify_key(key) if not key_info: raise ApiError("API key parameter '%s' is invalid" % key, 401) g.user = key_info.user g.customers = [key_info.customer] if key_info.customer else [] g.scopes = key_info.scopes if not Permission.is_in_scope(scope, g.scopes): raise ApiError('Missing required scope: %s' % scope, 403) else: return f(*args, **kwargs) # Bearer Token auth_header = request.headers.get('Authorization', '') m = re.match(r'Bearer (\S+)', auth_header) token = m.group(1) if m else None if token: try: jwt = Jwt.parse(token) except DecodeError: raise ApiError('Token is invalid', 401) except ExpiredSignature: raise ApiError('Token has expired', 401) except InvalidAudience: raise ApiError('Invalid audience', 401) g.user = jwt.preferred_username g.customers = jwt.customers g.scopes = jwt.scopes if not Permission.is_in_scope(scope, g.scopes): raise ApiError('Missing required scope: %s' % scope, 403) else: return f(*args, **kwargs) # Basic Auth auth_header = request.headers.get('Authorization', '') m = re.match(r'Basic (\S+)', auth_header) credentials = m.group(1) if m else None if credentials: try: username, password = base64.b64decode(credentials).decode( 'utf-8').split(':') except Exception as e: raise BasicAuthError('Invalid credentials', 400, errors=[str(e)]) user = User.check_credentials(username, password) if not user: raise BasicAuthError('Authorization required', 401) if current_app.config[ 'EMAIL_VERIFICATION'] and not user.email_verified: raise BasicAuthError('email not verified', 401) if not_authorized('ALLOWED_EMAIL_DOMAINS', groups=[user.domain]): raise BasicAuthError('Unauthorized domain', 403) g.user = user.email g.customers = get_customers(user.email, groups=[user.domain]) g.scopes = Permission.lookup(user.email, groups=user.roles) if not Permission.is_in_scope(scope, g.scopes): raise BasicAuthError('Missing required scope: %s' % scope, 403) else: return f(*args, **kwargs) if not current_app.config['AUTH_REQUIRED']: g.user = None g.customers = [] g.scopes = [] return f(*args, **kwargs) # Google App Engine Cron Service if request.headers.get('X-Appengine-Cron', False) and request.headers.get( 'X-Forwarded-For', '') == '0.1.0.1': return f(*args, **kwargs) raise ApiError('Missing authorization API Key or Bearer Token', 401)
def wrapped(*args, **kwargs): # API Key (Authorization: Key <key>) if 'Authorization' in request.headers: auth_header = request.headers['Authorization'] m = re.match(r'Key (\S+)', auth_header) key = m.group(1) if m else None # API Key (X-API-Key: <key>) elif 'X-API-Key' in request.headers: key = request.headers['X-API-Key'] # API Key (/foo?api-key=<key>) else: key = request.args.get('api-key', None) if key: key_info = ApiKey.verify_key(key) if not key_info: raise ApiError("API key parameter '%s' is invalid" % key, 401) g.user_id = None g.login = key_info.user g.customers = [key_info.customer] if key_info.customer else [] g.scopes = key_info.scopes # type: List[Scope] if not Permission.is_in_scope(scope, have_scopes=g.scopes): raise ApiError('Missing required scope: %s' % scope.value, 403) else: return f(*args, **kwargs) # Bearer Token auth_header = request.headers.get('Authorization', '') m = re.match(r'Bearer (\S+)', auth_header) token = m.group(1) if m else None if token: try: jwt = Jwt.parse(token) except DecodeError: raise ApiError('Token is invalid', 401) except ExpiredSignature: raise ApiError('Token has expired', 401) except InvalidAudience: raise ApiError('Invalid audience', 401) g.user_id = jwt.subject g.login = jwt.preferred_username g.customers = jwt.customers g.scopes = jwt.scopes # type: List[Scope] if not Permission.is_in_scope(scope, have_scopes=g.scopes): raise ApiError('Missing required scope: %s' % scope.value, 403) else: return f(*args, **kwargs) # Basic Auth auth_header = request.headers.get('Authorization', '') m = re.match(r'Basic (\S+)', auth_header) credentials = m.group(1) if m else None if credentials: try: username, password = base64.b64decode(credentials).decode('utf-8').split(':') except Exception as e: raise BasicAuthError('Invalid credentials', 400, errors=[str(e)]) user = User.check_credentials(username, password) if not user: raise BasicAuthError('Authorization required', 401) if current_app.config['EMAIL_VERIFICATION'] and not user.email_verified: raise BasicAuthError('email not verified', 401) if not_authorized('ALLOWED_EMAIL_DOMAINS', groups=[user.domain]): raise BasicAuthError('Unauthorized domain', 403) g.user_id = user.id g.login = user.email g.customers = get_customers(user.email, groups=[user.domain]) g.scopes = Permission.lookup(user.email, roles=user.roles) # type: List[Scope] if not Permission.is_in_scope(scope, have_scopes=g.scopes): raise BasicAuthError('Missing required scope: %s' % scope.value, 403) else: return f(*args, **kwargs) if not current_app.config['AUTH_REQUIRED']: g.user_id = None g.login = None g.customers = [] g.scopes = [] # type: List[Scope] return f(*args, **kwargs) # Google App Engine Cron Service if request.headers.get('X-Appengine-Cron', False) and request.headers.get('X-Forwarded-For', '') == '0.1.0.1': return f(*args, **kwargs) raise ApiError('Missing authorization API Key or Bearer Token', 401)
def wrapped(*args, **kwargs): # API Key (Authorization: Key <key>) if 'Authorization' in request.headers and request.headers[ 'Authorization'].startswith('Key '): auth_header = request.headers['Authorization'] m = re.match(r'Key (\S+)', auth_header) key = m.group(1) if m else None # API Key (X-API-Key: <key>) elif 'X-API-Key' in request.headers: key = request.headers['X-API-Key'] # API Key (/foo?api-key=<key>) else: key = request.args.get('api-key', None) if key: key_info = ApiKey.verify_key(key) if not key_info: raise ApiError("API key parameter '%s' is invalid" % key, 401) g.user_id = None g.login = key_info.user g.customers = [key_info.customer] if key_info.customer else [] g.scopes = key_info.scopes # type: List[Scope] if not Permission.is_in_scope(scope, have_scopes=g.scopes): raise ApiError('Missing required scope: %s' % scope, 403) else: return f(*args, **kwargs) # Hawk HMAC Signature (Authorization: Hawk mac=...) if request.headers.get('Authorization', '').startswith('Hawk'): try: receiver = HmacAuth.authenticate(request) except mohawk.exc.HawkFail as e: raise ApiError(str(e), 401) g.user_id = None g.login = receiver.parsed_header.get('id') g.customers = [] g.scopes = ADMIN_SCOPES return f(*args, **kwargs) # Bearer Token auth_header = request.headers.get('Authorization', '') m = re.match(r'Bearer (\S+)', auth_header) token = m.group(1) if m else None if token: try: jwt = Jwt.parse(token) except DecodeError: raise ApiError('Token is invalid', 401) except ExpiredSignatureError: raise ApiError('Token has expired', 401) except InvalidAudienceError: raise ApiError('Invalid audience', 401) g.user_id = jwt.oid or jwt.subject g.login = jwt.preferred_username g.customers = jwt.customers g.scopes = jwt.scopes # type: List[Scope] if not Permission.is_in_scope(scope, have_scopes=g.scopes): raise ApiError('Missing required scope: %s' % scope, 403) else: return f(*args, **kwargs) # Basic Auth auth_header = request.headers.get('Authorization', '') m = re.match(r'Basic (\S+)', auth_header) credentials = m.group(1) if m else None if credentials: try: username, password = base64.b64decode(credentials).decode( 'utf-8').split(':') except Exception as e: raise BasicAuthError('Invalid credentials', 400, errors=[str(e)]) user = User.check_credentials(username, password) if not user: raise BasicAuthError('Authorization required', 401) if current_app.config[ 'EMAIL_VERIFICATION'] and not user.email_verified: raise BasicAuthError('email not verified', 401) if not_authorized('ALLOWED_EMAIL_DOMAINS', groups=[user.domain]): raise BasicAuthError('Unauthorized domain', 403) g.user_id = user.id g.login = user.email g.customers = get_customers(user.email, groups=[user.domain]) g.scopes = Permission.lookup( user.email, roles=user.roles) # type: List[Scope] if not Permission.is_in_scope(scope, have_scopes=g.scopes): raise BasicAuthError('Missing required scope: %s' % scope, 403) else: return f(*args, **kwargs) # auth not required if not current_app.config['AUTH_REQUIRED']: g.user_id = None g.login = None g.customers = [] g.scopes = [] # type: List[Scope] return f(*args, **kwargs) # auth required for admin/write, but readonly is allowed if current_app.config['AUTH_REQUIRED'] and current_app.config[ 'ALLOW_READONLY']: g.user_id = None g.login = None g.customers = [] g.scopes = current_app.config['READONLY_SCOPES'] return f(*args, **kwargs) # Google App Engine Cron Service if request.headers.get('X-Appengine-Cron', False) and request.headers.get( 'X-Forwarded-For', '') == '0.1.0.1': return f(*args, **kwargs) raise ApiError('Missing authorization API Key or Bearer Token', 401)