Skip to content

Consider storing the "adjusted" return type for function literals #2709

@dcreager

Description

@dcreager

@carljm suggested this in https://github.com/astral-sh/ruff/pull/22954/changes#r2760401929.

(Once that PR merges) we (will) have a post-processing step that adjusts the return type of a function definition in some situations. In particular, we detect when some of the typevars in the function definition are actually bound by a return type Callable, instead of the function itself:

def decorator_factory[T]() -> Callable[[T], T]:
    ...

This is implemented as a post-processing step when we lazily construct the function definition's Signature. Even after that PR, we infer and store a type for the return type AST node (Callable[[T], T]) before that post-processing step — in this case, a non-generic Callable.

We should probably store the modified type instead. This will primarily benefit the LSP hover information for the return type annotation.

Some complications:

  • We currently generate this lazily during Signature generation, which is needed since we need to look at all of the parameters, as well, to determine which typevars are not bound in enclosing scopes, and don't appear outside of return type Callables. But we need to infer/store a type for each AST node eagerly during TypeInferenceBuilder.

  • Another adjustment that we perform is to wrap return types for async functions in CoroutineType. We should not include that adjustment in the type that we store for the return type AST node. (This is handled by having both a signature and raw signature for each function.)

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions