def from_func(cls, func): if not hasattr(func, cls.__ANNOTATION_BUILDER_KEY): spec = utils.get_arg_spec(func) handler = cls(func, spec.args) setattr(func, cls.__ANNOTATION_BUILDER_KEY, handler) handler.set_annotations(spec.annotations) return getattr(func, cls.__ANNOTATION_BUILDER_KEY)
def __call__(self, func): spec = utils.get_arg_spec(func) arg_handler = types.ArgumentAnnotationHandlerBuilder(func, spec.args) builder = RequestDefinitionBuilder( self._method, URIDefinitionBuilder(self._uri), arg_handler, decorators.MethodAnnotationHandlerBuilder()) arg_handler.add_annotations_from_spec(spec) if spec.return_annotation is not None: builder = decorators.returns(spec.return_annotation)(builder) functools.update_wrapper(builder, func) return builder
def test_get_arg_spec(): if is_py2: code = "def func(pos1, *args, **kwargs): pass" else: code = "def func(pos1, *args: 2, **kwargs: 3) -> 4: pass" exec(code, globals(), locals()) signature = utils.get_arg_spec(locals()["func"]) assert isinstance(signature, utils.Signature) assert signature.args == ["pos1", "args", "kwargs"] if not is_py2: assert signature.annotations == {"args": 2, "kwargs": 3} assert signature.return_annotation == 4
def __call__(self, func): spec = utils.get_arg_spec(func) arg_handler = types.ArgumentAnnotationHandlerBuilder(func, spec.args) method_handler = decorators.MethodAnnotationHandlerBuilder() builder = RequestDefinitionBuilder(self._method, URIDefinitionBuilder(self._uri), arg_handler, method_handler) if spec.args: # Ignore `self` instance reference spec.annotations.pop(spec.args[0], None) arg_handler.set_annotations(spec.annotations) if spec.return_annotation is not None: builder = decorators.returns(spec.return_annotation)(builder) functools.update_wrapper(builder, func) return builder
def __call__(self, func): spec = utils.get_arg_spec(func) arg_handler = arguments.ArgumentAnnotationHandlerBuilder( func, spec.args) builder = RequestDefinitionBuilder( self._method, URIDefinitionBuilder(self._uri), arg_handler, decorators.MethodAnnotationHandlerBuilder(), ) # Need to add the annotations after constructing the request # definition builder so it has a chance to attach its listener. arg_handler.set_annotations(spec.annotations) # Use return value type hint as expected return type if spec.return_annotation is not None: builder = returns.schema(spec.return_annotation)(builder) functools.update_wrapper(builder, func) builder = self._add_args(builder) return builder