Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Calculating the complexity of decorator functions with nested functions #158

Open
tuze-kuyucu opened this issue Oct 31, 2018 · 2 comments
Open

Comments

@tuze-kuyucu
Copy link

Radon returns cc value of A for decorators with inner functions, I guess this is a known issue. Is there any planned support for this?

@rubik
Copy link
Owner

rubik commented Jan 26, 2019

I apologize for the long delay. Could you elaborate on the issue? It's possible that a decorator contains inner functions and still have a total CC such that the rank is A.

@tuze-kuyucu
Copy link
Author

Hi!
Here is the function in question, which radon ranks with an A:

def event(use_annotations=False) -> Callable[[F], F]:
    def decorator(f: F) -> F:
        sig = signature(f)
        if use_annotations:
            params: Dict[str, fields.Field] = OrderedDict()
            for name, param in sig.parameters.items():
                if name == "self":
                    continue
                annotation = param.annotation
                default = param.default
                if annotation == Parameter.empty:
                    allow_none = default is None
                    if default == Parameter.empty:
                        params[name] = fields.Field(required=True, allow_none=allow_none)
                    else:
                        params[name] = fields.Field(required=True, allow_none=allow_none, missing=default)
                else:
                    params[name] = make_field_from_type_annotation(annotation, default)
            class_name = "".join(x.capitalize() for x in f.__name__.split("_")) + "Schema"
            params["Meta"] = Meta
            schema_class = type(class_name, (Schema,), params)
            schema = schema_class()
        else:
            schema_class = None
            schema = None

        @functools.wraps(f)
        def wrapper(self, *args, **kwargs):
            return_value = f(self, *args, **kwargs)
            bound = sig.bind(self, *args, **kwargs)
            arguments = bound.arguments
            del arguments["self"]
            if schema:
                result = schema.dumps(arguments)
                if result.errors:
                    raise ValueError(str(result.errors))
                dumps = result.data
            else:
                dumps = mujson.dumps(arguments)
            self._uncommitted_events.append(
                Event(
                    type=f.__name__,
                    stream_kind=self.STREAM_KIND,
                    stream_id=self._id,
                    data=dumps.encode(),
                ))
            return return_value

        cast(Any, wrapper).schema_class = schema_class
        cast(Any, wrapper).schema = schema
        return cast(F, wrapper)

    return decorator

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants