The intention was to implement some sort of plugin framework, where plugins are subclasses (i.e. B) of the same base class (i.e. A). The base class is loaded with standard import, whereas subclasses are loaded with imp.load_module() from the path of a well-known package (i.e. pkg).
pkg/
__init__.py
mod1.py
class A
mod2.py
class B(pkg.mod1.A)
This worked fine with real subclasses, i.e.,
# test_1.py
import pkg
from pkg import mod1
import imp
tup = imp.find_module('mod2', pkg.__path__)
mod2 = imp.load_module('mod2', tup[0], tup[1], tup[2])
print(issubclass(mod2.B, mod1.A)) # True
But the problem came when testing the base class itself,
# test_2.py
import pkg
from pkg import mod1
import imp
tup = imp.find_module('mod1', pkg.__path__)
mod0 = imp.load_module('mod1', tup[0], tup[1], tup[2])
print(issubclass(mod0.A, mod1.A)) # False
But mod0.A and mod1.A are actually the same class from the same file (pkg/mod1.py).
This issue appears in both python 2.7 and 3.2.
Now the question is two-fold, a) Is it an expected feature or a bug of issubclass(), and b) How to get rid of this without changing contents of pkg?
They aren’t the same class. They were created with the same code, but since you executed that code twice (once in the import and once in load_module) you get two different class objects.
issubclassis comparing the identities of the class objects and they’re different.Edit: since you can’t rely on
issubclass, one possible alternative is to create a unique attribute on the base class that will be inherited by the derived classes. This attribute will exist on copies of the class as well. You can then test for the attribute.