ariadne
ariadne copied to clipboard
Make Resolver type definition more accurate
Our current type for Resolver is Callable[..., Any], catching any arguments and relasing anything.
This is because its currently impossible to tpe Callable that accepts *args or **kwagrs.
This issue is [known to MyPy authors](https://github.com/python/typing/issues/264 but a the time of writing no solution is available.
This is related to #79
This is achievable via Protocol.
@rafalp Let me know if the definitions below would be correct.
class Resolver(Protocol):
def __call__(self, obj: Any, info: GraphQLResolveInfo, **kwargs: Any) -> Any:
pass
class TypeResolver(Protocol):
def __call__(self, obj: Any, *_: Any) -> Optional[str]:
pass
If so, I'd love to make a contribution.
EDIT There are already some decent type definitions in graphql-core.
# Note: Contrary to the Javascript implementation of GraphQLFieldResolver,
# the context is passed as part of the GraphQLResolveInfo and any arguments
# are passed individually as keyword arguments.
GraphQLFieldResolverWithoutArgs = Callable[[Any, GraphQLResolveInfo], Any]
# Unfortunately there is currently no syntax to indicate optional or keyword
# arguments in Python, so we also allow any other Callable as a workaround:
GraphQLFieldResolver = Callable[..., Any]
# Note: Contrary to the Javascript implementation of GraphQLTypeResolver,
# the context is passed as part of the GraphQLResolveInfo:
GraphQLTypeResolver = Callable[
[Any, GraphQLResolveInfo, "GraphQLAbstractType"],
AwaitableOrValue[Optional[Union["GraphQLObjectType", str]]],
]
However, GraphQLFieldResolver could also be more accurate.
Should ariadne import types from graphql-core or use its own definitions?
Anyway, the Resolver type definition could be rewritten to:
class Resolver(Protocol):
def __call__(self, obj: Any, info: GraphQLResolveInfo, **kwargs: Any) -> Any:
pass
We could use type definitions from graphql-core and and run extra checks on our side at type's definition time.