Exemplo n.º 1
0
def register_service_views(config, service):
    """Register the routes of the given service into the pyramid router.

    :param config: the pyramid configuration object that will be populated.
    :param service: the service object containing the definitions
    """
    services = config.registry.setdefault('cornice_services', {})
    prefix = config.route_prefix or ''
    services[prefix + service.path] = service

    # keep track of the registered routes
    registered_routes = []

    # before doing anything else, register a view for the OPTIONS method
    # if we need to
    if service.cors_enabled and 'OPTIONS' not in service.defined_methods:
        service.add_view('options', view=get_cors_preflight_view(service))

    # register the fallback view, which takes care of returning good error
    # messages to the user-agent
    cors_validator = get_cors_validator(service)

    # Cornice-specific arguments that pyramid does not know about
    cornice_parameters = ('filters', 'validators', 'schema', 'klass',
                          'error_handler', 'deserializer') + CORS_PARAMETERS

    for method, view, args in service.definitions:

        args = copy.copy(args)  # make a copy of the dict to not modify it
        # Deepcopy only the params we're possibly passing on to pyramid
        # (Some of those in cornice_parameters, e.g. ``schema``, may contain
        # unpickleable values.)
        for item in args:
            if item not in cornice_parameters:
                args[item] = copy.deepcopy(args[item])

        args['request_method'] = method

        if service.cors_enabled:
            args['validators'].insert(0, cors_validator)

        decorated_view = decorate_view(view, dict(args), method)

        for item in cornice_parameters:
            if item in args:
                del args[item]

        # if acl is present, then convert it to a "factory"
        if 'acl' in args:
            args["factory"] = make_route_factory(args.pop('acl'))

        # 1. register route
        route_args = {}
        if 'factory' in args:
            route_args['factory'] = args.pop('factory')

        if 'traverse' in args:
            route_args['traverse'] = args.pop('traverse')

        # register the route name with the path if it's not already done
        if service.path not in registered_routes:
            config.add_route(service.name, service.path, **route_args)
            config.add_view(view=get_fallback_view(service),
                            route_name=service.name)
            registered_routes.append(service.path)
            config.commit()

        # 2. register view(s)
        # pop and compute predicates which get passed through to Pyramid 1:1

        predicate_definitions = _pop_complex_predicates(args)

        if predicate_definitions:
            for predicate_list in predicate_definitions:
                args = dict(args)  # make a copy of the dict to not modify it

                # prepare view args by evaluating complex predicates
                _mungle_view_args(args, predicate_list)

                # We register the same view multiple times with different
                # accept / content_type / custom_predicates arguments
                config.add_view(view=decorated_view,
                                route_name=service.name,
                                **args)

        else:
            # it is a simple view, we don't need to loop on the definitions
            # and just add it one time.
            config.add_view(view=decorated_view,
                            route_name=service.name,
                            **args)

        config.commit()
Exemplo n.º 2
0
def register_service_views(config, service):
    """Register the routes of the given service into the pyramid router.

    :param config: the pyramid configuration object that will be populated.
    :param service: the service object containing the definitions
    """
    services = config.registry.setdefault('cornice_services', {})
    services[service.path] = service

    # keep track of the registered routes
    registered_routes = []

    # before doing anything else, register a view for the OPTIONS method
    # if we need to
    if service.cors_enabled and 'OPTIONS' not in service.defined_methods:
        service.add_view('options', view=get_cors_preflight_view(service))

    # register the fallback view, which takes care of returning good error
    # messages to the user-agent
    cors_validator = get_cors_validator(service)
    cors_filter = get_cors_filter(service)

    for method, view, args in service.definitions:

        args = copy.deepcopy(args)  # make a copy of the dict to not modify it
        args['request_method'] = method

        if service.cors_enabled:
            args['validators'].insert(0, cors_validator)
            args['filters'].append(cors_filter)

        decorated_view = decorate_view(view, dict(args), method)

        for item in ('filters', 'validators', 'schema', 'klass',
                     'error_handler') + CORS_PARAMETERS:
            if item in args:
                del args[item]

        # if acl is present, then convert it to a "factory"
        if 'acl' in args:
            args["factory"] = make_route_factory(args.pop('acl'))

        route_args = {}
        if 'factory' in args:
            route_args['factory'] = args.pop('factory')

        # register the route name with the path if it's not already done
        if service.path not in registered_routes:
            config.add_route(service.path, service.path, **route_args)
            config.add_view(view=get_fallback_view(service),
                            route_name=service.path)
            registered_routes.append(service.path)

        # loop on the accept fields: we need to build custom predicate if
        # callables were passed
        if 'accept' in args:
            for accept in to_list(args.pop('accept', ())):
                predicates = args.get('custom_predicates', [])
                if callable(accept):
                    predicate_checker = functools.partial(match_accept_header,
                                                          accept)
                    predicates.append(predicate_checker)
                    args['custom_predicates'] = predicates
                else:
                    # otherwise it means that it is a "standard" accept,
                    # so add it as such.
                    args['accept'] = accept

                # We register multiple times the same view with different
                # accept / custom_predicates arguments
                config.add_view(view=decorated_view, route_name=service.path,
                                **args)
        else:
            # it is a simple view, we don't need to loop on the definitions
            # and just add it one time.
            config.add_view(view=decorated_view, route_name=service.path,
                            **args)
Exemplo n.º 3
0
def register_service_views(config, service):
    """Register the routes of the given service into the pyramid router.

    :param config: the pyramid configuration object that will be populated.
    :param service: the service object containing the definitions
    """
    route_name = service.name
    services = config.registry.cornice_services
    prefix = config.route_prefix or ''
    services[prefix + service.path] = service

    # before doing anything else, register a view for the OPTIONS method
    # if we need to
    if service.cors_enabled and 'OPTIONS' not in service.defined_methods:
        service.add_view('options',
                         view=get_cors_preflight_view(service),
                         permission=NO_PERMISSION_REQUIRED)

    # register the fallback view, which takes care of returning good error
    # messages to the user-agent
    cors_validator = get_cors_validator(service)

    # Cornice-specific arguments that pyramid does not know about
    cornice_parameters = ('filters', 'validators', 'schema', 'klass',
                          'error_handler', 'deserializer') + CORS_PARAMETERS

    # 1. register route

    route_args = {}

    if hasattr(service, 'acl'):
        route_args['factory'] = make_route_factory(service.acl)

    elif hasattr(service, 'factory'):
        route_args['factory'] = service.factory

    if hasattr(service, 'traverse'):
        route_args['traverse'] = service.traverse

    routes = config.get_predlist('route')
    for predicate in routes.sorter.names:
        if hasattr(service, predicate):
            route_args[predicate] = getattr(service, predicate)

    config.add_route(route_name, service.path, **route_args)

    # 2. register view(s)

    for method, view, args in service.definitions:

        args = copy.copy(args)  # make a copy of the dict to not modify it
        # Deepcopy only the params we're possibly passing on to pyramid
        # (Some of those in cornice_parameters, e.g. ``schema``, may contain
        # unpickleable values.)
        for item in args:
            if item not in cornice_parameters:
                args[item] = copy.deepcopy(args[item])

        args['request_method'] = method

        if service.cors_enabled:
            args['validators'].insert(0, cors_validator)

        decorated_view = decorate_view(view, dict(args), method)

        for item in cornice_parameters:
            if item in args:
                del args[item]

        # These attributes are used in routes not views
        deprecated_attrs = ['acl', 'factory', 'traverse']
        for attr in deprecated_attrs:
            if attr in args:
                args.pop(attr)

        # filter predicates defined on Resource
        route_predicates = config.get_predlist('route').sorter.names
        view_predicates = config.get_predlist('view').sorter.names
        for pred in set(route_predicates).difference(view_predicates):
            if pred in args:
                args.pop(pred)

        # pop and compute predicates which get passed through to Pyramid 1:1

        predicate_definitions = _pop_complex_predicates(args)

        if predicate_definitions:
            for predicate_list in predicate_definitions:
                args = dict(args)  # make a copy of the dict to not modify it

                # prepare view args by evaluating complex predicates
                _mungle_view_args(args, predicate_list)

                # We register the same view multiple times with different
                # accept / content_type / custom_predicates arguments
                config.add_view(view=decorated_view,
                                route_name=route_name,
                                **args)

        else:
            # it is a simple view, we don't need to loop on the definitions
            # and just add it one time.
            config.add_view(view=decorated_view, route_name=route_name, **args)

        config.commit()

    if service.definitions:
        # Add the fallback view last
        config.add_view(view=get_fallback_view(service),
                        route_name=route_name,
                        permission=NO_PERMISSION_REQUIRED)
        config.commit()
Exemplo n.º 4
0
def register_service_views(config, service):
    """Register the routes of the given service into the pyramid router.

    :param config: the pyramid configuration object that will be populated.
    :param service: the service object containing the definitions
    """
    route_name = service.name
    services = config.registry.cornice_services
    prefix = config.route_prefix or ''
    services[prefix + service.path] = service

    # before doing anything else, register a view for the OPTIONS method
    # if we need to
    if service.cors_enabled and 'OPTIONS' not in service.defined_methods:
        service.add_view('options', view=get_cors_preflight_view(service),
                         permission=NO_PERMISSION_REQUIRED)

    # register the fallback view, which takes care of returning good error
    # messages to the user-agent
    cors_validator = get_cors_validator(service)

    # Cornice-specific arguments that pyramid does not know about
    cornice_parameters = ('filters', 'validators', 'schema', 'klass',
                          'error_handler', 'deserializer') + CORS_PARAMETERS

    # 1. register route

    route_args = {}

    if hasattr(service, 'acl'):
        route_args['factory'] = make_route_factory(service.acl)

    elif hasattr(service, 'factory'):
        route_args['factory'] = service.factory

    if hasattr(service, 'traverse'):
        route_args['traverse'] = service.traverse

    config.add_route(route_name, service.path, **route_args)

    # 2. register view(s)

    for method, view, args in service.definitions:

        args = copy.copy(args)  # make a copy of the dict to not modify it
        # Deepcopy only the params we're possibly passing on to pyramid
        # (Some of those in cornice_parameters, e.g. ``schema``, may contain
        # unpickleable values.)
        for item in args:
            if item not in cornice_parameters:
                args[item] = copy.deepcopy(args[item])

        args['request_method'] = method

        if service.cors_enabled:
            args['validators'].insert(0, cors_validator)

        decorated_view = decorate_view(view, dict(args), method)

        for item in cornice_parameters:
            if item in args:
                del args[item]

        # These attributes are used in routes not views
        deprecated_attrs = ['acl', 'factory', 'traverse']
        for attr in deprecated_attrs:
            if attr in args:
                args.pop(attr)

        # pop and compute predicates which get passed through to Pyramid 1:1

        predicate_definitions = _pop_complex_predicates(args)

        if predicate_definitions:
            for predicate_list in predicate_definitions:
                args = dict(args)  # make a copy of the dict to not modify it

                # prepare view args by evaluating complex predicates
                _mungle_view_args(args, predicate_list)

                # We register the same view multiple times with different
                # accept / content_type / custom_predicates arguments
                config.add_view(view=decorated_view, route_name=route_name,
                                **args)

        else:
            # it is a simple view, we don't need to loop on the definitions
            # and just add it one time.
            config.add_view(view=decorated_view, route_name=route_name,
                            **args)

        config.commit()

    if service.definitions:
        # Add the fallback view last
        config.add_view(view=get_fallback_view(service),
                        route_name=route_name,
                        permission=NO_PERMISSION_REQUIRED)
        config.commit()
Exemplo n.º 5
0
def register_service_views(config, service):
    """Register the routes of the given service into the pyramid router.

    :param config: the pyramid configuration object that will be populated.
    :param service: the service object containing the definitions
    """
    services = config.registry.setdefault('cornice_services', {})
    services[service.path] = service

    # keep track of the registered routes
    registered_routes = []

    # before doing anything else, register a view for the OPTIONS method
    # if we need to
    if service.cors_enabled and 'OPTIONS' not in service.defined_methods:
        service.add_view('options', view=get_cors_preflight_view(service))

    # register the fallback view, which takes care of returning good error
    # messages to the user-agent
    cors_validator = get_cors_validator(service)

    for method, view, args in service.definitions:

        args = copy.deepcopy(args)  # make a copy of the dict to not modify it
        args['request_method'] = method

        if service.cors_enabled:
            args['validators'].insert(0, cors_validator)

        decorated_view = decorate_view(view, dict(args), method)

        for item in ('filters', 'validators', 'schema', 'klass',
                     'error_handler') + CORS_PARAMETERS:
            if item in args:
                del args[item]

        # if acl is present, then convert it to a "factory"
        if 'acl' in args:
            args["factory"] = make_route_factory(args.pop('acl'))


        # 1. register route

        route_args = {}
        if 'factory' in args:
            route_args['factory'] = args.pop('factory')

        # register the route name with the path if it's not already done
        if service.path not in registered_routes:
            config.add_route(service.name, service.path, **route_args)
            config.add_view(view=get_fallback_view(service),
                            route_name=service.name)
            registered_routes.append(service.path)
            config.commit()


        # 2. register view(s)

        # pop and compute predicates which get passed through to Pyramid 1:1
        predicate_definitions = _pop_complex_predicates(args)

        if predicate_definitions:
            for predicate_list in predicate_definitions:
                args = dict(args)  # make a copy of the dict to not modify it

                # prepare view args by evaluating complex predicates
                _mungle_view_args(args, predicate_list)

                # We register the same view multiple times with different
                # accept / content_type / custom_predicates arguments
                config.add_view(view=decorated_view, route_name=service.name,
                            **args)

        else:
            # it is a simple view, we don't need to loop on the definitions
            # and just add it one time.
            config.add_view(view=decorated_view, route_name=service.name,
                            **args)

        config.commit()
Exemplo n.º 6
0
def register_service_views(config, service):
    """Register the routes of the given service into the pyramid router.

    :param config: the pyramid configuration object that will be populated.
    :param service: the service object containing the definitions
    """
    route_name = service.name
    existing_route = service.pyramid_route
    prefix = config.route_prefix or ''
    services = config.registry.cornice_services
    if existing_route:
        route_name = existing_route
        services[prefix + '__cornice' + existing_route] = service
    else:
        services[prefix + service.path] = service

    # before doing anything else, register a view for the OPTIONS method
    # if we need to
    if service.cors_enabled and 'OPTIONS' not in service.defined_methods:
        service.add_view('options', view=get_cors_preflight_view(service),
                         permission=NO_PERMISSION_REQUIRED)

    # register the fallback view, which takes care of returning good error
    # messages to the user-agent
    cors_validator = get_cors_validator(service)

    # Cornice-specific arguments that pyramid does not know about
    cornice_parameters = ('filters', 'validators', 'schema', 'klass',
                          'error_handler') + CORS_PARAMETERS

    # 1. register route

    route_args = {}

    if hasattr(service, 'factory'):
        route_args['factory'] = service.factory

    routes = config.get_predlist('route')
    for predicate in routes.sorter.names:
        # Do not let the custom predicates handle validation of Header Accept,
        # which will pass it through to pyramid. It is handled by
        # _fallback_view(), because it allows callable.
        if predicate == 'accept':
            continue

        if hasattr(service, predicate):
            route_args[predicate] = getattr(service, predicate)

    # register route when not using exiting pyramid routes
    if not existing_route:
        config.add_route(route_name, service.path, **route_args)

    # 2. register view(s)

    for method, view, args in service.definitions:

        args = copy.copy(args)  # make a copy of the dict to not modify it
        # Deepcopy only the params we're possibly passing on to pyramid
        # (Some of those in cornice_parameters, e.g. ``schema``, may contain
        # unpickleable values.)
        for item in args:
            if item not in cornice_parameters:
                args[item] = copy.deepcopy(args[item])

        args['request_method'] = method

        if service.cors_enabled:
            args['validators'].insert(0, cors_validator)

        decorated_view = decorate_view(view, dict(args), method, route_args)

        for item in cornice_parameters:
            if item in args:
                del args[item]

        # filter predicates defined on Resource
        route_predicates = config.get_predlist('route').sorter.names
        view_predicates = config.get_predlist('view').sorter.names
        for pred in set(route_predicates).difference(view_predicates):
            if pred in args:
                args.pop(pred)

        # pop and compute predicates which get passed through to Pyramid 1:1

        predicate_definitions = _pop_complex_predicates(args)

        if predicate_definitions:
            empty_contenttype = [({'kind': 'content_type', 'value': ''},)]
            for predicate_list in predicate_definitions + empty_contenttype:
                args = dict(args)  # make a copy of the dict to not modify it

                # prepare view args by evaluating complex predicates
                _mungle_view_args(args, predicate_list)

                # We register the same view multiple times with different
                # accept / content_type / custom_predicates arguments
                config.add_view(view=decorated_view, route_name=route_name,
                                **args)

        else:
            # it is a simple view, we don't need to loop on the definitions
            # and just add it one time.
            config.add_view(view=decorated_view, route_name=route_name,
                            **args)

    if service.definitions:
        # Add the fallback view last
        config.add_view(view=get_fallback_view(service),
                        route_name=route_name,
                        permission=NO_PERMISSION_REQUIRED,
                        require_csrf=False)
Exemplo n.º 7
0
def register_service_views(config, service):
    """Register the routes of the given service into the pyramid router.

    :param config: the pyramid configuration object that will be populated.
    :param service: the service object containing the definitions
    """
    services = config.registry.setdefault('cornice_services', {})
    services[service.path] = service

    # keep track of the registered routes
    registered_routes = []

    # before doing anything else, register a view for the OPTIONS method
    # if we need to
    if service.cors_enabled and 'OPTIONS' not in service.defined_methods:
        service.add_view('options', view=get_cors_preflight_view(service))

    # register the fallback view, which takes care of returning good error
    # messages to the user-agent
    cors_validator = get_cors_validator(service)

    for method, view, args in service.definitions:

        args = copy.deepcopy(args)  # make a copy of the dict to not modify it
        args['request_method'] = method

        if service.cors_enabled:
            args['validators'].insert(0, cors_validator)

        decorated_view = decorate_view(view, dict(args), method)

        for item in ('filters', 'validators', 'schema', 'klass',
                     'error_handler') + CORS_PARAMETERS:
            if item in args:
                del args[item]

        # if acl is present, then convert it to a "factory"
        if 'acl' in args:
            args["factory"] = make_route_factory(args.pop('acl'))

        route_args = {}
        if 'factory' in args:
            route_args['factory'] = args.pop('factory')

        # register the route name with the path if it's not already done
        if service.path not in registered_routes:
            config.add_route(service.name, service.path, **route_args)
            config.add_view(view=get_fallback_view(service),
                            route_name=service.name)
            registered_routes.append(service.path)

        # loop on the accept fields: we need to build custom predicate if
        # callables were passed
        if 'accept' in args:
            for accept in to_list(args.pop('accept', ())):
                predicates = args.get('custom_predicates', [])
                if callable(accept):
                    predicate_checker = functools.partial(match_accept_header,
                                                          accept)
                    predicates.append(predicate_checker)
                    args['custom_predicates'] = predicates
                else:
                    # otherwise it means that it is a "standard" accept,
                    # so add it as such.
                    args['accept'] = accept

                # We register multiple times the same view with different
                # accept / custom_predicates arguments
                config.add_view(view=decorated_view, route_name=service.name,
                                **args)
        else:
            # it is a simple view, we don't need to loop on the definitions
            # and just add it one time.
            config.add_view(view=decorated_view, route_name=service.name,
                            **args)