Open Viicos opened 1 year ago
I would welcome a generic as described by the OP. However, I would discourage allowing "any user defined object" since the click docs clearly indicate that ctx.obj
is a dict
type. As such, I wouldn't want the ability for ctx.obj
to be, for example, a list
.
Alternatively, the typing could allow any subclass of click.Context
. That way code like the following could be used to define custom context schemas.
import click
from typing import TypedDict
class MyContextObj(TypedDict):
foo: int
bar: str
class MyContext(click.Context)
obj: MyContextObj
@click.command()
@click.pass_context
def my_command(ctx: MyContext):
ctx.obj # Type checkers can tell that this has keys `foo: int` and `bar: str`
Unfortunately, this code currently throws the following typing error when checked by mypy
:
Argument 1 to "pass_context" has incompatible type "Callable[[MyContext, Iterable[str]], Any]"; expected "Callable[[Context, Iterable[str]], Any]"
Pleasantly surprised to see some people are also looking for this. I'll look into this this week and will come with a PR that will hopefully be accepted.
Unfortunately, this code currently throws the following typing error when checked by
mypy
:
This can be fixed by using a TypeVar
in the pass_context
signature, however I don't think this is a great idea, as this isn't type safe: at runtime, ctx
is still an instance of Context
.
the click docs clearly indicate that
ctx.obj
is adict
type.
I couldn't find anything stating this. Do you know in which section of the docs this is described? The type hint for obj
is Any
, so I think you can allow any object.
the click docs clearly indicate that ctx.obj is a dict type.
I couldn't find anything stating this. Do you know in which section of the docs this is described? The type hint for obj is Any, so I think you can allow any object.
You appear to be correct. I was looking at the code example for Nested Handling and Contexts which includes an assertion that ctx.obj
is a dict
. That said, upon closer look it appears that one could assert that ctx.obj
is indeed any type.
To add some type safety to the
obj
attribute of theContext
class, I was thinking maybe it could be made generic with respect toobj
attribute. It could then be used this way (with aTypedDict
but it could be any user defined object):That might be a bit cumbersome, so I'd understand if this is rejected (but I'm open to alternatives). Otherwise, I will be happy to implement this