Open
Description
I hope this falls under the scope of this repo -
Is there any a way type-hint __array_namespace__
? Is it even possible to do so, and it needs to be standardized, or maybe it's not possible with current python type hinting system?
Motivation:
Suppose I want to write a function that will work in multiple conforming libraries, it will probably start with:
xp = x.__array_namespace__()
or, like in NEP-47:
def foo(x,y):
xp = get_namespace(x,y)
In both cases, I want to be able to type check xp
, and have auto-complete on xp
in the various IDEs. (At least some auto-complete engines relay on static typing e.g https://github.com/microsoft/pyright)
Is this possible?
Activity
BvB93 commentedon Sep 19, 2021
Unfortunately you can't return
Literal
modules (which would make this a lot easier), but when implementing the API it would be possible to define and return an auxiliary class that mirrors the content of the namespace.BvB93 commentedon Sep 19, 2021
Small update: unfortunately python/mypy#708 was never completelly fixed, so you'd have to return
type[_ArrayAPINameSpace]
in the case of mypy, otherwise it will interpret the namespace functions as normal methods and strip their first argument.asmeurer commentedon Sep 20, 2021
This issue is also somewhat related #229
gilfree commentedon Sep 29, 2021
Hi @BvB93,
Thanks for the answer.
Are there any thoughts about making such a type/class part of the standard (It may be helpful for statically checking conformance)?
BvB93 commentedon Sep 29, 2021
My personal thoughts: the standard currently specifies that
__array_namespace__
should return "an object representing the array API namespace", so concrete API implementations should have enough flexibility to use this little type-checking trick if they'd so desire.gilfree commentedon Sep 29, 2021
Thanks @BvB93
BvB93 commentedon Nov 22, 2021
Recently the
__getattr__
method totypes.ModuleType
in typeshed (xref python/typeshed#6302), meaning that all modulegetattr
operations lacking a dedicated set of annotations will returnAny
.Now, while this is by no means as good as a dedicated type representing the namespaces' content, it does provide a notable improvement over just returning
Any
(assuming the namespace is actually a module during runtime).rgommers commentedon Dec 1, 2021
That sounds like a good idea.
typeshed
isn't a common dependency though for libraries. Is it going to land intyping_extensions
? What should we do with this issue, reopen to keep track of the idea?BvB93 commentedon Dec 1, 2021
So
typeshed
is the official repro containing annotations for the standard library, copies of which are vendored by most (all?) type checkers. While you could manually update it, it's general generally more convenient to just wait until mypy and the likes have a new release.It might be worthwhile, though I don't expect any major breakthroughs without a mypy plugin of some sort. While comparatively minor, the upstream
types.ModuleType
change is still a nice bonus.rgommers commentedon Dec 2, 2021
Ah okay, got it now -
types.ModuleType
is already in the stdlib for Python 3.8, so it's fine for us to use it now. And Mypy et al. supporting the newgetattr
behavior will materialize. So I'd say let's useModuleType
as the annotation for the return type in implementations where the return type is actually a module.Note that in the standard, the docs now say
**out**: _<object>_
and I'm not sure we can do better there (aside from a recommendation), because the returned object doesn't need to be a module, it could be a class instance for example.BvB93 commentedon Dec 15, 2021
I feel that
Any
would be a small improvement overobject
here; it is designed as the ultimate placeholder, used for situations situation wherein some specific(-ish) type is involved, but you're not sure how to express it. In contrast,object
is generally reserved for situation wherein truly any arbitrary object is considered valid.Change the type annotation for `__array_namespace__` to Any
14 remaining items