On Thu, Dec 10, 2020 at 1:22 PM Steven D'Aprano <st...@pearwood.info> wrote:
> On Thu, Dec 10, 2020 at 10:57:32AM -0800, Guido van Rossum wrote: > > > All I have to add is that I am appalled that people actually write `from > > foo import __init__` > > I too would be appalled if that was what people are doing, but it isn't. > > Looking at the code samples in the wild: > > https://github.com/search?l=Python&q=%22from+.__init__+import%22&type=Code > > I see no examples of either of the (anti-)patterns given by Gregory in > his opening post: > > # No examples of either of these. > from package import __init__ > import package.__init__ > > I have read through the first ten, and last five, pages of the search > results and what people are doing is typically: > > from __init__ import name > > or sometimes with a wildcard import. There are also a few cases using a > dot: > > from .__init__ import name > > and a few cases of attempted bilingual 2 and 3 code: > > try: > from .__init__ import name #Python 3 > except: > from __init__ import name > > > So what seems to be happening is that people have a package sub-module, > say "package/run.py", and in Python 2 code they wanted to import from > the main package from within run.py. > Interesting, since Python 2 also supports relative imports. That last example makes the intention clear(er) -- as you write they want it to work both when "run" is imported as a toplevel module and when it is located inside a package, i.e. "package.run". If all the other code is in __init__.py that trick will indeed work, but it points to a general lack of understanding of how packages and import path resolution works. :-( This would be unrelated to Python 3 (unless their app somehow also evolved so that their Python 2 version uses a flat namespace while their Python 3 version uses packages). > I don't know if that is less appalling than what Gregory has told us, > but it is different, and to my mind at least it makes it more > understandable and not as weird looking. > Well, if I really meant to do something like that I'd write try: from . import name except ImportError: from __init__ import name but I would never write from .__init__ import name > This is nothing like Gregory's characterisation of cargo cult (his term) > programmers writing `import package.__init__` to import package. > Well, depending on where you are in the stack, there may be no way to distinguish that from other forms involving a dot. > [...] > > As for how people can check whether a package is a namespace package, > there > > are many other ways to check for that without attempting to import > > `__init__` from it. > > Are these many other ways a secret? *wink* Because if somebody with the > experience and knowledge of MAL doesn't know them, let alone people like > me, maybe you should give us a hint what they are. > In the below example, foo is a namespace package and bar a classic package. Behold the differences: ``` Python 3.8.6 (tags/v3.8.6:db45529, Sep 23 2020, 15:52:53) [MSC v.1927 64 bit (AMD64)] on win32 Type "help", "copyright", "credits" or "license" for more information. >>> import foo, bar >>> foo <module 'foo' (namespace)> >>> bar <module 'bar' from 'C:\\Users\\gvanrossum\\cpython\\bar\\__init__.py'> >>> dir(foo) ['__doc__', '__file__', '__loader__', '__name__', '__package__', '__path__', '__spec__'] >>> dir(bar) ['__builtins__', '__cached__', '__doc__', '__file__', '__loader__', '__name__', '__package__', '__path__', '__spec__'] >>> foo.__file__ >>> bar.__file__ 'C:\\Users\\gvanrossum\\cpython\\bar\\__init__.py' >>> foo.__path__ _NamespacePath(['C:\\Users\\gvanrossum\\cpython\\foo']) >>> bar.__path__ ['C:\\Users\\gvanrossum\\cpython\\bar'] >>> ``` (Note that `foo.__file__` prints nothing because the value is None.) -- --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-change-the-world/>
_______________________________________________ Python-ideas mailing list -- python-ideas@python.org To unsubscribe send an email to python-ideas-le...@python.org https://mail.python.org/mailman3/lists/python-ideas.python.org/ Message archived at https://mail.python.org/archives/list/python-ideas@python.org/message/DA2E6PBGDFQ567UPFVPOJNKCRBTPWSFF/ Code of Conduct: http://python.org/psf/codeofconduct/