Пример #1
0
def generate_response_header_validator(headers, context, **kwargs):
    validators = ValidationDict()
    for key, header_definition in headers.items():
        # generate a function that will attempt to cast the header to the
        # appropriate type.
        header_processor = generate_value_processor(
            context=context,
            **header_definition
        )
        # generate a function that will validate the header.
        header_validator = functools.partial(
            validate_object,
            field_validators=construct_header_validators(header_definition, context=context),
        )
        # Chain the type casting function, the individual header validation
        # function with a methodcaller that will fetch the header with
        # `response.headers.get(header_name, EMPTY)` and then feed that into
        # the type casting function and then into the validation function.
        validators.add_validator(key, chain_reduce_partial(
            operator.methodcaller('get', key, EMPTY),
            header_processor,
            header_validator,
        ))
    return chain_reduce_partial(
        operator.attrgetter('headers'),
        functools.partial(validate_object, field_validators=validators),
    )
Пример #2
0
def generate_path_validator(api_path, path_definition, parameters,
                            context, **kwargs):
    """
    Generates a callable for validating the parameters in a response object.
    """
    path_level_parameters = dereference_parameter_list(
        path_definition.get('parameters', []),
        context,
    )
    operation_level_parameters = dereference_parameter_list(
        parameters,
        context,
    )

    all_parameters = merge_parameter_lists(
        path_level_parameters,
        operation_level_parameters,
    )

    # PATH
    in_path_parameters = filter_parameters(all_parameters, in_=PATH)
    return chain_reduce_partial(
        operator.attrgetter('path'),
        generate_path_parameters_validator(api_path, in_path_parameters, context),
    )
Пример #3
0
def generate_header_validator(headers, context, **kwargs):
    validators = {}
    for header_definition in headers:
        header_validator = functools.partial(
            validate_object,
            validators=construct_header_validators(header_definition, context=context),
            inner=True,
        )
        validators[header_definition['name']] = chain_reduce_partial(
            operator.methodcaller('get', header_definition['name'], EMPTY),
            header_validator,
        )
    return chain_reduce_partial(
        operator.attrgetter('headers'),
        functools.partial(validate_object, validators=validators, inner=True),
    )
Пример #4
0
def generate_value_processor(type_,
                             collectionFormat=None,
                             items=None,
                             **kwargs):
    """
    Create a callable that will take the string value of a header and cast it
    to the appropriate type.  This can involve:

    - splitting a header of type 'array' by its delimeters.
    - type casting the internal elements of the array.
    """
    processors = []
    if is_non_string_iterable(type_):
        assert False, "This should not be possible"
    else:
        if type_ == ARRAY and collectionFormat:
            delimeter = DELIMETERS[collectionFormat]
            # split the string based on the delimeter specified by the
            # `collectionFormat`
            processors.append(operator.methodcaller('split', delimeter))
            # remove any Falsy values like empty strings.
            processors.append(functools.partial(filter, bool))
            # strip off any whitespace
            processors.append(
                functools.partial(map, operator.methodcaller('strip')))
            if items is not None:
                if isinstance(items, collections.Mapping):
                    items_processors = itertools.repeat(
                        generate_value_processor(**items))
                elif isinstance(items, collections.Sequence):
                    items_processors = itertools.chain(
                        (generate_value_processor(**item) for item in items),
                        itertools.repeat(lambda v: v),
                    )
                elif isinstance(items, six.string_types):
                    raise NotImplementedError("Not implemented")
                else:
                    assert False, "Should not be possible"
                # 1. zip the processor and the array items together
                # 2. apply the processor to each array item.
                # 3. cast the starmap generator to a list.
                processors.append(
                    chain_reduce_partial(
                        functools.partial(zip, items_processors),
                        functools.partial(itertools.starmap,
                                          lambda fn, v: fn(v)),
                        list,
                    ))
        else:
            processors.append(
                functools.partial(cast_value_to_type, type_=type_))

    def processor(value, **kwargs):
        try:
            return chain_reduce_partial(*processors)(value)
        except (ValueError, TypeError):
            return value

    return processor
Пример #5
0
def generate_value_processor(type_, collectionFormat=None, items=None, **kwargs):
    """
    Create a callable that will take the string value of a header and cast it
    to the appropriate type.  This can involve:

    - splitting a header of type 'array' by its delimeters.
    - type casting the internal elements of the array.
    """
    processors = []
    if is_non_string_iterable(type_):
        assert False, "This should not be possible"
    else:
        if type_ == ARRAY and collectionFormat:
            delimeter = DELIMETERS[collectionFormat]
            # split the string based on the delimeter specified by the
            # `collectionFormat`
            processors.append(operator.methodcaller('split', delimeter))
            # remove any Falsy values like empty strings.
            processors.append(functools.partial(filter, bool))
            # strip off any whitespace
            processors.append(functools.partial(map, operator.methodcaller('strip')))
            if items is not None:
                if isinstance(items, collections.Mapping):
                    items_processors = itertools.repeat(
                        generate_value_processor(**items)
                    )
                elif isinstance(items, collections.Sequence):
                    items_processors = itertools.chain(
                        (generate_value_processor(**item) for item in items),
                        itertools.repeat(lambda v: v),
                    )
                elif isinstance(items, six.string_types):
                    raise NotImplementedError("Not implemented")
                else:
                    assert False, "Should not be possible"
                # 1. zip the processor and the array items together
                # 2. apply the processor to each array item.
                # 3. cast the starmap generator to a list.
                processors.append(
                    chain_reduce_partial(
                        functools.partial(zip, items_processors),
                        functools.partial(itertools.starmap, lambda fn, v: fn(v)),
                        list,
                    )
                )
        else:
            processors.append(
                functools.partial(cast_value_to_type, type_=type_)
            )

    def processor(value, **kwargs):
        try:
            return chain_reduce_partial(*processors)(value)
        except (ValueError, TypeError):
            return value

    return processor
Пример #6
0
def generate_request_content_type_validator(consumes, **kwargs):
    validator = functools.partial(
        validate_request_content_type,
        content_types=consumes,
    )
    return chain_reduce_partial(
        operator.attrgetter('request'),
        validator,
    )
Пример #7
0
def generate_response_body_validator(schema, context, **kwargs):
    return chain_reduce_partial(
        attrgetter('data'),
        functools.partial(
            validate_object,
            schema=schema,
            context=context,
        ),
    )
Пример #8
0
def generate_response_body_validator(schema, context, **kwargs):
    return chain_reduce_partial(
        operator.attrgetter('data'),
        functools.partial(
            validate_object,
            schema=schema,
            context=context,
        ),
    )
Пример #9
0
def generate_response_body_validator(schema, context, inner=False):
    validators = construct_schema_validators(schema, context=context)
    return chain_reduce_partial(
        operator.attrgetter('data'),
        functools.partial(
            validate_object,
            validators=validators,
            inner=True,
        ),
    )
Пример #10
0
def generate_query_parameters_validator(query_parameters, context):
    query_parameter_validator = functools.partial(
        validate_query_parameters,
        query_parameters=query_parameters,
        context=context,
        inner=True,
    )
    return chain_reduce_partial(
        operator.attrgetter('query_data'),
        query_parameter_validator,
    )
Пример #11
0
def generate_response_header_validator(headers, context, **kwargs):
    validators = {}
    for key, header_definition in headers.items():
        header_validator = functools.partial(
            validate_object,
            validators=construct_header_validators(header_definition, context=context),
            inner=True,
        )
        # Chain the individual header validation function with a methodcaller
        # that will fetch the header with
        # `response.headers.get(header_name, EMPTY)`
        # and then feed that into the validation function.
        validators[key] = chain_reduce_partial(
            operator.methodcaller('get', key, EMPTY),
            header_validator,
        )
    return chain_reduce_partial(
        operator.attrgetter('headers'),
        functools.partial(validate_object, validators=validators, inner=True),
    )
Пример #12
0
def generate_response_validator(schema, **kwargs):
    response_validator = functools.partial(
        validate_response,
        paths=schema['paths'],
        base_path=schema.get('basePath', ''),
        context=schema,
        **kwargs
    )
    return chain_reduce_partial(
        normalize_response,
        response_validator,
    )
Пример #13
0
def test_chain_reduce_partial():
    def fn_a(v):
        return v * 3

    def fn_b(v):
        return v * 5

    fn_c = chain_reduce_partial(fn_a, fn_b)

    for _ in range(100):
        v = random.randint(-1000000, 1000000)
        assert fn_c(v) == fn_b(fn_a(v))
Пример #14
0
def test_chain_reduce_partial():
    def fn_a(v):
        return v * 3

    def fn_b(v):
        return v * 5

    fn_c = chain_reduce_partial(fn_a, fn_b)

    for _ in range(100):
        v = random.randint(-1000000, 1000000)
        assert fn_c(v) == fn_b(fn_a(v))
Пример #15
0
def generate_path_parameters_validator(api_path, path_parameters, context):
    path_parameter_validator = functools.partial(
        validate_path_parameters,
        api_path=api_path,
        path_parameters=path_parameters,
        context=context,
        inner=True,
    )
    return chain_reduce_partial(
        operator.attrgetter('path'),
        path_parameter_validator,
    )
Пример #16
0
def generate_header_validator(headers, context, **kwargs):
    """
    Generates a validation function that will validate a dictionary of headers.
    """
    validators = ValidationDict()
    for header_definition in headers:
        header_processor = generate_value_processor(context=context, **header_definition)
        header_validator = generate_object_validator(
            field_validators=construct_header_validators(header_definition, context=context)
        )
        validators.add_property_validator(
            header_definition["name"], chain_reduce_partial(header_processor, header_validator)
        )
    return generate_object_validator(field_validators=validators)
Пример #17
0
def generate_header_validator(headers, context, **kwargs):
    """
    Generates a validation function that will validate a dictionary of headers.
    """
    validators = ValidationDict()
    for header_definition in headers:
        header_processor = generate_value_processor(context=context,
                                                    **header_definition)
        header_validator = generate_object_validator(
            field_validators=construct_header_validators(header_definition,
                                                         context=context), )
        validators.add_property_validator(
            header_definition['name'],
            chain_reduce_partial(
                header_processor,
                header_validator,
            ),
        )
    return generate_object_validator(field_validators=validators)
Пример #18
0
def generate_parameters_validator(api_path, path_definition, parameters, context, **kwargs):
    """
    Generates a validator function to validate.

    - request.path against the path parameters.
    - request.query against the query parameters.
    - TODO: request.headers against the header parameters.
    - TODO: request.body against the body parameters.
    - TODO: request.formData against any form data.
    """
    validators = {}
    path_level_parameters = path_definition.get('parameters', [])
    operation_level_parameters = parameters

    all_parameters = merge_parameter_lists(
        path_level_parameters,
        operation_level_parameters,
    )

    # PATH
    in_path_parameters = filter_parameters(all_parameters, in_=PATH)
    validators['path'] = generate_path_parameters_validator(
        api_path, in_path_parameters, context,
    )

    # QUERY
    in_query_parameters = filter_parameters(all_parameters, in_=QUERY)
    validators['query'] = generate_query_parameters_validator(in_query_parameters, context)

    # HEADERS
    in_header_parameters = filter_parameters(all_parameters, in_=HEADER)
    validators['headers'] = generate_header_validator(in_header_parameters, context)

    return chain_reduce_partial(
        operator.attrgetter('request'),
        functools.partial(validate_request_parameters, validators=validators),
    )
Пример #19
0
 def processor(value, **kwargs):
     try:
         return chain_reduce_partial(*processors)(value)
     except (ValueError, TypeError):
         return value
Пример #20
0
def generate_parameters_validator(api_path, path_definition, parameters,
                                  context, **kwargs):
    """
    Generates a validator function to validate.

    - request.path against the path parameters.
    - request.query against the query parameters.
    - request.headers against the header parameters.
    - TODO: request.body against the body parameters.
    - TODO: request.formData against any form data.
    """
    # TODO: figure out how to merge this with the same code in response
    # validation.
    validators = ValidationDict()
    path_level_parameters = dereference_parameter_list(
        path_definition.get('parameters', []),
        context,
    )
    operation_level_parameters = dereference_parameter_list(
        parameters,
        context,
    )

    all_parameters = merge_parameter_lists(
        path_level_parameters,
        operation_level_parameters,
    )

    # PATH
    in_path_parameters = filter_parameters(all_parameters, in_=PATH)
    validators.add_validator(
        'path',
        chain_reduce_partial(
            operator.attrgetter('path'),
            generate_path_parameters_validator(api_path, in_path_parameters,
                                               context),
        ),
    )

    # QUERY
    in_query_parameters = filter_parameters(all_parameters, in_=QUERY)
    validators.add_validator(
        'query',
        chain_reduce_partial(
            operator.attrgetter('query_data'),
            functools.partial(
                validate_query_parameters,
                query_parameters=in_query_parameters,
                context=context,
            ),
        ),
    )

    # HEADERS
    in_header_parameters = filter_parameters(all_parameters, in_=HEADER)
    validators.add_validator(
        'headers',
        chain_reduce_partial(
            operator.attrgetter('headers'),
            generate_header_validator(in_header_parameters, context),
        ),
    )

    # FORM_DATA
    # in_form_data_parameters = filter_parameters(all_parameters, in_=FORM_DATA)
    # validators.add_validator(
    #     'form_data',
    #     chain_reduce_partial(
    #         operator.attrgetter('data'),
    #         generate_form_data_validator(in_form_data_parameters, context),
    #     )
    # )

    # REQUEST_BODY
    in_request_body_parameters = filter_parameters(all_parameters, in_=BODY)
    validators.add_validator(
        'request_body',
        chain_reduce_partial(
            operator.attrgetter('data'),
            generate_request_body_validator(in_request_body_parameters,
                                            context),
        ))

    return generate_object_validator(field_validators=validators)
Пример #21
0
 def processor(value, **kwargs):
     try:
         return chain_reduce_partial(*processors)(value)
     except (ValueError, TypeError):
         return value
Пример #22
0
def generate_parameters_validator(api_path, path_definition, parameters, context, **kwargs):
    """
    Generates a validator function to validate.

    - request.path against the path parameters.
    - request.query against the query parameters.
    - request.headers against the header parameters.
    - TODO: request.body against the body parameters.
    - TODO: request.formData against any form data.
    """
    # TODO: figure out how to merge this with the same code in response
    # validation.
    validators = ValidationDict()
    path_level_parameters = dereference_parameter_list(path_definition.get("parameters", []), context)
    operation_level_parameters = dereference_parameter_list(parameters, context)

    all_parameters = merge_parameter_lists(path_level_parameters, operation_level_parameters)

    # PATH
    in_path_parameters = filter_parameters(all_parameters, in_=PATH)
    validators.add_validator(
        "path",
        chain_reduce_partial(
            operator.attrgetter("path"), generate_path_parameters_validator(api_path, in_path_parameters, context)
        ),
    )

    # QUERY
    in_query_parameters = filter_parameters(all_parameters, in_=QUERY)
    validators.add_validator(
        "query",
        chain_reduce_partial(
            operator.attrgetter("query_data"),
            functools.partial(validate_query_parameters, query_parameters=in_query_parameters, context=context),
        ),
    )

    # HEADERS
    in_header_parameters = filter_parameters(all_parameters, in_=HEADER)
    validators.add_validator(
        "headers",
        chain_reduce_partial(operator.attrgetter("headers"), generate_header_validator(in_header_parameters, context)),
    )

    # FORM_DATA
    # in_form_data_parameters = filter_parameters(all_parameters, in_=FORM_DATA)
    # validators.add_validator(
    #     'form_data',
    #     chain_reduce_partial(
    #         operator.attrgetter('data'),
    #         generate_form_data_validator(in_form_data_parameters, context),
    #     )
    # )

    # REQUEST_BODY
    in_request_body_parameters = filter_parameters(all_parameters, in_=BODY)
    validators.add_validator(
        "request_body",
        chain_reduce_partial(
            operator.attrgetter("data"), generate_request_body_validator(in_request_body_parameters, context)
        ),
    )

    return generate_object_validator(field_validators=validators)