I'm trying to figure out why the behavior of issubclass() changes based on how a class was imported.
I have the following setup
proj
|_pkg
|_ __init__.py
|_ base.py
|_ child.py
base.py has
class Base(object):
pass
child.py has
from base import Base
class Child(Base):
pass
Then I do the following in shell:
$export PYTHONPATH='/tmp/proj'
$ipython
In [1]: from pkg.base import Base as Base1
In [2]: from base import Base as Base2
In [3]: from pkg.child import Child as Child1
In [4]: from child import Child as Child2
In [5]: issubclass(Child1, Base1)
Out[5]: True # Makes Sense
In [6]: issubclass(Child1, Base2)
Out[6]: False # Confused. Why would this be False.
In [7]: issubclass(Child2, Base1)
Out[7]: False # Confused. Why would this be False.
In [8]: issubclass(Child2, Base2)
Out[8]: True
I'm confused by whats going on in In [6] and [7]. I would expect those to be True too.
After some digging around found the answer here - http://python-notes.curiousefficiency.org/en/latest/python_concepts/import_traps.html#the-double-import-trap
This next trap exists in all current versions of Python, including 3.3, and can be summed up in the following general guideline: “Never add a package directory, or any directory inside a package, directly to the Python path”.
The reason this is problematic is that every module in that directory is now potentially accessible under two different names: as a top level module (since the directory is on sys.path) and as a submodule of the package (if the higher level directory containing the package itself is also on sys.path).
As an example, Django (up to and including version 1.3) used to be guilty of setting up exactly this situation for site-specific applications - the application ends up being accessible as both app and site.app in the module namespace, and these are actually two different copies of the module.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With