Import hook for a shim. This ensures that submodule imports return the real target module, not a clone that will confuse `is` and `isinstance` checks.
| 14 | """A warning to show when a module has moved, and a shim is in its place.""" |
| 15 | |
| 16 | class ShimImporter(object): |
| 17 | """Import hook for a shim. |
| 18 | |
| 19 | This ensures that submodule imports return the real target module, |
| 20 | not a clone that will confuse `is` and `isinstance` checks. |
| 21 | """ |
| 22 | def __init__(self, src, mirror): |
| 23 | self.src = src |
| 24 | self.mirror = mirror |
| 25 | |
| 26 | def _mirror_name(self, fullname): |
| 27 | """get the name of the mirrored module""" |
| 28 | |
| 29 | return self.mirror + fullname[len(self.src):] |
| 30 | |
| 31 | def find_module(self, fullname, path=None): |
| 32 | """Return self if we should be used to import the module.""" |
| 33 | if fullname.startswith(self.src + '.'): |
| 34 | mirror_name = self._mirror_name(fullname) |
| 35 | try: |
| 36 | mod = import_item(mirror_name) |
| 37 | except ImportError: |
| 38 | return |
| 39 | else: |
| 40 | if not isinstance(mod, types.ModuleType): |
| 41 | # not a module |
| 42 | return None |
| 43 | return self |
| 44 | |
| 45 | def load_module(self, fullname): |
| 46 | """Import the mirrored module, and insert it into sys.modules""" |
| 47 | mirror_name = self._mirror_name(fullname) |
| 48 | mod = import_item(mirror_name) |
| 49 | sys.modules[fullname] = mod |
| 50 | return mod |
| 51 | |
| 52 | |
| 53 | class ShimModule(types.ModuleType): |