"""Module for requests validation.""" from functools import wraps from jsonschema import validate from jsonschema import ValidationError from oto import response from oto.adaptors.flask import flaskify as oto_flaskify from assets.constants import field_const from assets.constants import error as error_const from assets.validation.schema import header def validate_headers(request, required=True): """A decorator to call when validating HTTP request headers. Args: request (werkzeug.local.LocalProxy): request object from the handler. Returns: callable: the wrapped function. """ def wrap(function): @wraps(function) def wrapped_f(*args, **kwargs): if required or (not required and field_const.ORCHARD_USER_ID in request.headers): try: validate(dict(request.headers), header.user_headers_schema) except ValidationError as error: return oto_flaskify( response.create_error_response( code=error_const.ERROR_CODE_HEADER_VALIDATION, message=str(error))) return function(*args, **kwargs) return wrapped_f return wrap def validate_body(request, schema): """A decorator to call when validating HTTP request body. Args: request (werkzeug.local.LocalProxy): Request object from the handler. schema (Draft4Validator): The JSON Draft4 Schema to validate against. Returns: callable: the wrapped function. """ def wrap(function): @wraps(function) def wrapped_f(*args, **kwargs): try: validate(request.get_json(), schema) except ValidationError as error: return oto_flaskify( response.create_error_response( code=error_const.ERROR_CODE_BODY_VALIDATION, message=str(error))) return function(*args, **kwargs) return wrapped_f return wrap def validate_query(request, schema): """A decorator to call when validating query arguments. Args: request (werkzeug.local.LocalProxy): Request object from the handler. schema (Draft4Validator): The JSON Draft4 Schema to validate against. Returns: callable: the wrapped function. """ def wrap(function): @wraps(function) def wrapped_f(*args, **kwargs): try: source_query = dict(request.args) query_dict = {k: (v[0] if len(v) == 1 else v) for k, v in source_query.items()} validate(query_dict, schema) except ValidationError as error: return oto_flaskify( response.create_error_response( code=error_const.ERROR_CODE_QUERY_VALIDATION, message=str(error))) return function(*args, **kwargs) return wrapped_f return wrap