Why doesn't `from pkg import mod' work after `del pkg.mod'?

ryles rylesny at gmail.com
Fri Jul 24 21:11:29 EDT 2009


According to http://www.python.org/doc/essays/packages.html:

"The import statement first tests whether the item is defined in the
package; if not, it assumes it is a module and attempts to load it."

However, I've noticed that once a module is imported using the
`from pkg import mod' syntax, if its name is deleted from the
package namespace then subsequent imports with `from' will fail.

Here is an example of this type of scenario:

$ ls -l pkg
total 8.0K
-rw-rw-r-- 1 ? general   0 Jul 24 20:21 _impl.py
-rw-rw-r-- 1 ? general 147 Jul 24 20:28 __init__.py
-rw-rw-r-- 1 ? general   0 Jul 24 20:33 public2.py
-rw-rw-r-- 1 ? general 208 Jul 24 20:32 public.py

$ cat pkg/__init__.py
from pkg import _impl

# Add functions which refer to objects in _impl
# ...

# Don't "currently" require this in the namespace anymore.
del _impl

$ cat pkg/public.py
# Implement something with the aid of _impl.

from pkg import public2  # OK, fine.
from pkg import _impl    # The module exists, but this will fail.
# Could do import pkg._impl (or a relative import)

$ python
Python 2.6.2 (r262:71600, Jul 16 2009, 14:04:28)
[GCC 4.1.2 20071124 (Red Hat 4.1.2-42)] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> from pkg import public
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "pkg/public.py", line 4, in <module>
    from pkg import _impl    # The module exists, but this will fail.
ImportError: cannot import name _impl
>>> import sys
>>> sys.modules["pkg._impl"]
<module 'pkg._impl' from 'pkg/_impl.py'>
>>> from pkg import _impl
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: cannot import name _impl
>>> import pkg._impl  # Giving up!
>>>

I had previously noted that once a module is imported from a package
it is automatically added to the package namespace:

>>> import pkg
>>> dir(pkg)
['__builtins__', '__doc__', '__file__', '__name__', '__package__',
'__path__']
>>> from pkg import public2
>>> dir(pkg)
['__builtins__', '__doc__', '__file__', '__name__', '__package__',
'__path__', 'public2']
>>>

However, I didn't expect python to give up on importing those names
again
once removed.

Can anyone provide more details on what's occurring here?

Is this behavior intentional (a feature), or, is it in your opinion, a
defect?



More information about the Python-list mailing list