
On Sun, Mar 14, 2021 at 7:11 AM Theia Vogel <theia@vgel.me> wrote:
import the_module
the_module.sys
would work, but
from the_module import sys
would not work?
That might be odd and confusing.
Good point. I'm not familiar with CPython internals so I'm not sure how this would work on the implementation side, but I definitely think it would be important to not have an inconsistency here.
You probably should design this in partnership with someone who's more familiar with those internals. I believe that familiarity with Python internals is pretty important if you want to be able to design a new feature. Without thinking about the implementation you might design something that's awkward to implement; but you might also not think of something that's easy to do in the implementation but not obvious from superficial usage. (There are two lines in the Zen of Python devoted to this. :-) It is already possible to completely customize what happens when you write "import X". The returned object doesn't even strictly need to have a `__dict__` attribute. For `from X import Y` it first does `import X` (but doesn't bind X in your namespace) and then gives you `X.Y`, except if `Y` is `*`, in which case it looks in `X.__all__`, or if that's not found it looks in `X.__dict__` and imports all keys not starting with `_`. So to support `from X import *` you need either `__all__` or `__dict__`, else you get an import error (but neither of those is needed to support `from X import Y` or `import X; X.Y`). So I think there is no technical reason why we couldn't make it so that a module that uses `export` returns a proxy that only lets you use attributes that are explicitly exported. If users disagree with this, they can negotiate directly with the module authors. It's not a principle of Python that users *must* be given access to implementation details, after all -- it was just more convenient to do it this way when the language was young. (For example, it's not possible to root around like this in C extensions -- these only export what the author intends to export.) I do think that this means that existing libraries need to be careful when adding `export` statements, because it effectively becomes a backwards incompatibility. We could also implement a flag to weaken the strictness in this area (the flag would have to be set by the module, not by the importing code). Such a proxy could also be used to implement lazy imports, to some extent. (I'm not sure how to do `from X import Y` lazily -- it would have to wrap `Y` in another proxy, and then it becomes awkward, e.g. if `Y` is supposed to represent a simple number or string -- we don't want any other part of the language or stdlib to need to become aware of such proxies.) Long answer short, yes, we can make it so that `the_module.sys` in your example above is forbidden -- if we want to. -- --Guido van Rossum (python.org/~guido) *Pronouns: he/him **(why is my pronoun here?)* <http://feministing.com/2015/02/03/how-using-they-as-a-singular-pronoun-can-c...>