Reputation: 55
During the build process of a Python application I need to ignore some imports (because these modules are created by the build process). It is a chicken-and-egg-question, that I can't resolve easily. So I thought I could use the import hook to do this like this:
class ImportBlocker(object):
def __init__(self, *args):
self.module_names = args
def find_module(self, fullname, path=None):
if fullname in self.module_names:
return self
return None
def load_module(self, name):
raise ImportError("%s is blocked and cannot be imported" % name)
import sys
sys.meta_path = [ImportBlocker('chickenlib')]
But because I raise an error the build process stop --- I just want to silently ignore the import ... returning "None" does not work, too. Is there a way to do this?
Upvotes: 2
Views: 10350
Reputation: 396
Referring to "silently ignore the import", you can try this:
def TryImport(module_name):
try:
import module_name
except ImportError:
pass #or anything to log
Upvotes: 1
Reputation: 23216
If you are working on Python 3.4 or greater than you can "silently ignore" an import by altering your example just slightly to implement an exec_module
that will create an empty module.
class ImportBlocker(object):
def __init__(self, *args):
self.module_names = args
def find_module(self, fullname, path=None):
if fullname in self.module_names:
return self
return None
def exec_module(self, mdl):
# return an empty namespace
return {}
Now:
>>> import sys
>>> sys.meta_path = [ImportBlocker('chickenlib')]
>>> # this will work fine
>>> import chickenlib
>>> # there is nothing useful in your imported module
>>> print(vars(chickenlib))
{'__doc__': None, '__package__': '', '__name__': 'chickenlib', '__loader__': <__main__.ImportBlocker object at 0x102b8c470>, '__spec__': ModuleSpec(name='chickenlib', loader=<__main__.ImportBlocker object at 0x102b8c470>)}
Upvotes: 2