This is a somewhat tricky issue as python will not be interested in reloading the __builtin__
module as it hasn't changed. You will be forced to delete the __builtin__
module so as to force python to reimport it. You can also bypass __import__
by using importlib
(only true in python3, in python2 importlib
resorts to __import__
).
import sys
import importlib
import __builtin__ as old_builtins
class ExampleImporter(object):
old_import = __import__
def __init__(self):
self.count = 0
def new_import(self, *args, **kwargs):
self.count += 1
print(args, kwargs)
return self.old_import(*args, **kwargs)
importer = ExampleImporter()
old_builtins.__import__ = importer.new_import
assert __import__ == importer.new_import
# remove builtins from modules so as to force its reimport
del sys.modules["__builtin__"]
# in python3 the following bypasses __import__ entirely, but not in python2
new_builtins = importlib.import_module("__builtin__")
# restore initial state of __builtin__ module (will not delete new names
# added to __builtin__)
old_builtins.__dict__.update(new_builtins.__dict__)
# Replace new __builtin__ with old __builtin__ module. Otherwise you'll end up with a
# mess where different modules have different a __builtin__ module.
sys.modules["__builtin__"] = old_builtins
del new_builtins
assert __import__ == importer.old_import
assert importer.count == 1 # would be 0 in python3