Skip to content

Explore better typing for comprehensions / computational expressions #14

Open
@virusdave

Description

@virusdave

Consider:

    @effect.option
    def fn() -> Generator[Any, Any, List[str]]:
        x: int = yield 42
        y: str = yield f"{x} as a string"
        z: List[str] = yield from Some([y, str(x)])
        return z

Currently, unless each expression has the same type, you're stuck either being untyped or Any-typed and manually typing each bound name. This is really unfortunate and not at all type-safe.

Chaining a bunch of transformations of values within a functor or monad is a very common use of Haskell do-expressions, Scala for-expressions, and presumably (although i have no first hand knowledge) F# computational expressions.

It's really nice to be able to chain these and rely on types to ensure the correctness of each step.

With the current approach, it doesn't seem possible to type the individual layers of unwrapping differently unless they all share the same contained type (for the contravariant type parameter). This is really limiting the usefulness, alas.

Context: I'm trying to introduce some good foundations and abstractions for correctness at my company, and I think Expression could be a part of this based on its trajectory. However, the current limitations/ergonomics like this, combined with limitations in mypy would make this a somewhat difficult sell, so I'm hoping there's a better approach or some ideas for improvement. Happy to assist where possible, but i'm definitely not an expert in python or python typing.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions