Skip to content

Commit 3adccbd

Browse files
committed
-
1 parent 894f34d commit 3adccbd

File tree

1 file changed

+1
-152
lines changed

1 file changed

+1
-152
lines changed

python_toolbox/import_tools.py

Lines changed: 1 addition & 152 deletions
Original file line numberDiff line numberDiff line change
@@ -124,158 +124,7 @@ def exists(module_name, path=None):
124124
'''
125125
if '.' in module_name:
126126
raise NotImplementedError
127-
module_file = None
128-
try:
129-
module_file, _, _ = find_module(module_name, path=path,
130-
legacy_output=True)
131-
except ImportError:
132-
return False
133-
else:
134-
return True
135-
finally:
136-
if hasattr(module_file, 'close'):
137-
module_file.close()
138-
139-
140-
def _import_by_path_from_zip(path):
141-
'''Import a module from a path inside a zip file.'''
142-
assert '.zip' in path
143-
144-
parent_path, child_name = path.rsplit(os.path.sep, 1)
145-
zip_importer = zipimport.zipimporter(parent_path)
146-
module = zip_importer.load_module(child_name)
147-
148-
return module
149-
150-
151-
def import_by_path(path, name=None, keep_in_sys_modules=True):
152-
'''
153-
Import module/package by path.
154-
155-
You may specify a name: This is helpful only if it's an hierarchical name,
156-
i.e. a name with dots like "orange.claw.hammer". This will become the
157-
imported module's __name__ attribute. Otherwise only the short name,
158-
"hammer", will be used, which might cause problems in some cases. (Like
159-
when using multiprocessing.)
160-
'''
161-
path = pathlib.Path(path)
162-
if '.zip' in path:
163-
if name is not None:
164-
raise NotImplementedError
165-
module = _import_by_path_from_zip(path)
166-
167-
else: # '.zip' not in path
168-
short_name = path.stem
169-
170-
if name is None: name = short_name
171-
my_file = None
172-
try:
173-
(my_file, pathname, description) = \
174-
imp.find_module(short_name, [path.parent])
175-
module = imp.load_module(name, my_file, pathname, description)
176-
finally:
177-
if my_file is not None:
178-
my_file.close()
179-
180-
if not keep_in_sys_modules:
181-
del sys.modules[module.__name__]
182-
183-
return module
184-
185-
186-
def find_module(module_name, path=None, look_in_zip=True, legacy_output=False):
187-
'''
188-
Search for a module by name and return its filename.
189-
190-
When `path=None`, search for a built-in, frozen or special module and
191-
continue search in `sys.path`.
192-
193-
When `legacy_output=True`, instead of returning the module's filename,
194-
returns a tuple `(file, filename, (suffix, mode, type))`.
195-
196-
When `look_in_zip=True`, also looks in zipmodules.
197-
198-
todo: Gives funky output when `legacy_output=True and look_in_zip=True`.
199-
'''
200-
# todo: test
201-
if look_in_zip:
202-
try:
203-
result = _find_module_in_some_zip_path(module_name, path)
204-
except ImportError:
205-
pass
206-
else:
207-
return (None, result, None) if legacy_output else result
208-
209-
210-
if '.' in module_name:
211-
parent_name, child_name = module_name.rsplit('.', 1)
212-
parent_path = find_module(parent_name, path)
213-
result = imp.find_module(child_name, [parent_path])
214-
else:
215-
result = imp.find_module(module_name, path)
216-
217-
if legacy_output:
218-
return result
219-
else: # legacy_output is False
220-
file_, path_, description_ = result
221-
if file_ is not None:
222-
file_.close()
223-
return path_
224-
225-
226-
def _find_module_in_some_zip_path(module_name, path=None):
227-
'''
228-
If a module called `module_name` exists in a zip archive, get its path.
229-
230-
If the module is not found, raises `ImportError`.
231-
'''
232-
original_path_argument = path
233-
234-
if path is not None:
235-
zip_paths = path
236-
else:
237-
zip_paths = [path for path in sys.path if '.zip' in path]
238-
# todo: Find better way to filter zip paths.
239-
240-
for zip_path in zip_paths:
241-
242-
# Trying to create a zip importer:
243-
try:
244-
zip_importer = zipimport.zipimporter(zip_path)
245-
except zipimport.ZipImportError:
246-
continue
247-
# Excepted `ZipImportError` because we may have zip paths in
248-
# `sys.path` that don't really exist, which causes `zipimport` to
249-
# raise `ZipImportError`.
250-
#
251-
# todo: should find smarter way of catching this, excepting
252-
# `ZipImportError` is not a good idea.
253-
254-
result = zip_importer.find_module(
255-
# Python's zip importer stupidly needs us to replace dots with path
256-
# separators:
257-
_module_address_to_partial_path(module_name)
258-
)
259-
if result is None:
260-
continue
261-
else:
262-
assert result is zip_importer
263-
264-
#if '.' in module_name:
265-
#parent_package_name, child_module_name = \
266-
#module_name.rsplit('.')
267-
#leading_path = \
268-
#_module_address_to_partial_path(parent_package_name)
269-
#else:
270-
#leading_path = ''
271-
272-
return pathlib.Path(str(zip_path)) / \
273-
_module_address_to_partial_path(module_name)
274-
275-
if original_path_argument is not None:
276-
raise ImportError('Module not found in the given zip path.')
277-
else:
278-
raise ImportError('Module not found in any of the zip paths.')
127+
return bool(importlib.util.find_spec(module_name))
279128

280129

281130
def _module_address_to_partial_path(module_address):

0 commit comments

Comments
 (0)