blob: 0383c9a61b1ed1f51b583a2fe11f91a2c7749ed8 [file] [log] [blame]
Brett Cannon23cbd8a2009-01-18 00:24:28 +00001"""Core implementation of import.
2
3This module is NOT meant to be directly imported! It has been designed such
4that it can be bootstrapped into Python as the implementation of import. As
5such it requires the injection of specific modules and attributes in order to
6work. One should use importlib as the public-facing version of this module.
7
8"""
9
Brett Cannon7c9875c2009-03-04 01:10:09 +000010# Injected modules are '_warnings', 'imp', 'sys', 'marshal', 'errno', '_io',
11# and '_os' (a.k.a. 'posix', 'nt' or 'os2').
Brett Cannon23cbd8a2009-01-18 00:24:28 +000012# Injected attribute is path_sep.
13#
14# When editing this code be aware that code executed at import time CANNOT
15# reference any injected objects! This includes not only global code but also
16# anything specified at the class level.
17
18
Brett Cannonce43ddf2009-03-12 22:28:55 +000019# Bootstrap-related code ######################################################
20
Brett Cannon23cbd8a2009-01-18 00:24:28 +000021# XXX Could also expose Modules/getpath.c:joinpath()
22def _path_join(*args):
23 """Replacement for os.path.join."""
24 return path_sep.join(x[:-len(path_sep)] if x.endswith(path_sep) else x
25 for x in args)
26
27
28def _path_exists(path):
29 """Replacement for os.path.exists."""
30 try:
31 _os.stat(path)
32 except OSError:
33 return False
34 else:
35 return True
36
37
38def _path_is_mode_type(path, mode):
39 """Test whether the path is the specified mode type."""
40 try:
41 stat_info = _os.stat(path)
42 except OSError:
43 return False
44 return (stat_info.st_mode & 0o170000) == mode
45
46
47# XXX Could also expose Modules/getpath.c:isfile()
48def _path_isfile(path):
49 """Replacement for os.path.isfile."""
50 return _path_is_mode_type(path, 0o100000)
51
52
53# XXX Could also expose Modules/getpath.c:isdir()
54def _path_isdir(path):
55 """Replacement for os.path.isdir."""
56 return _path_is_mode_type(path, 0o040000)
57
58
59def _path_without_ext(path, ext_type):
60 """Replacement for os.path.splitext()[0]."""
Brett Cannon3eeaa0a2009-03-12 22:07:17 +000061 for suffix in _suffix_list(ext_type):
Brett Cannon23cbd8a2009-01-18 00:24:28 +000062 if path.endswith(suffix):
63 return path[:-len(suffix)]
64 else:
65 raise ValueError("path is not of the specified type")
66
67
68def _path_absolute(path):
69 """Replacement for os.path.abspath."""
70 if not path:
71 path = _os.getcwd()
72 try:
73 return _os._getfullpathname(path)
74 except AttributeError:
75 if path.startswith('/'):
76 return path
77 else:
78 return _path_join(_os.getcwd(), path)
79
80
Brett Cannon3eeaa0a2009-03-12 22:07:17 +000081class _closing:
Brett Cannon23cbd8a2009-01-18 00:24:28 +000082
83 """Simple replacement for contextlib.closing."""
84
85 def __init__(self, obj):
86 self.obj = obj
87
88 def __enter__(self):
89 return self.obj
90
91 def __exit__(self, *args):
92 self.obj.close()
93
94
Brett Cannon3eeaa0a2009-03-12 22:07:17 +000095def _wrap(new, old):
Brett Cannon51d8bfc2009-02-07 02:13:28 +000096 """Simple substitute for functools.wraps."""
97 for replace in ['__module__', '__name__', '__doc__']:
98 setattr(new, replace, getattr(old, replace))
99 new.__dict__.update(old.__dict__)
100
101
Brett Cannonce43ddf2009-03-12 22:28:55 +0000102# Finder/loader utility code ##################################################
103
Brett Cannon435aad82009-03-04 16:07:00 +0000104def set_package(fxn):
Brett Cannon06c9d962009-02-07 01:52:25 +0000105 """Set __package__ on the returned module."""
106 def wrapper(*args, **kwargs):
107 module = fxn(*args, **kwargs)
108 if not hasattr(module, '__package__') or module.__package__ is None:
109 module.__package__ = module.__name__
110 if not hasattr(module, '__path__'):
111 module.__package__ = module.__package__.rpartition('.')[0]
112 return module
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000113 _wrap(wrapper, fxn)
Brett Cannon06c9d962009-02-07 01:52:25 +0000114 return wrapper
115
116
Brett Cannon2cf03a82009-03-10 05:17:37 +0000117def set_loader(fxn):
118 """Set __loader__ on the returned module."""
119 def wrapper(self, *args, **kwargs):
120 module = fxn(self, *args, **kwargs)
121 if not hasattr(module, '__loader__'):
122 module.__loader__ = self
123 return module
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000124 _wrap(wrapper, fxn)
Brett Cannon2cf03a82009-03-10 05:17:37 +0000125 return wrapper
126
127
Brett Cannonce43ddf2009-03-12 22:28:55 +0000128def module_for_loader(fxn):
129 """Decorator to handle selecting the proper module for loaders.
130
131 Decorated modules are passed the module to use instead of the module name.
132 The module is either from sys.modules if it already exists (for reloading)
133 or is a new module which has __name__ set. If any exception is raised by
134 the decorated method and the decorator added a module to sys.modules, then
135 the module is deleted from sys.modules.
136
137 The decorator assumes that the decorated method takes self/cls as a first
138 argument and the module as the second argument.
139
140 """
141 def decorated(self, fullname):
142 module = sys.modules.get(fullname)
143 is_reload = bool(module)
144 if not is_reload:
145 # This must be done before open() is called as the 'io' module
146 # implicitly imports 'locale' and would otherwise trigger an
147 # infinite loop.
148 module = imp.new_module(fullname)
149 sys.modules[fullname] = module
150 try:
151 return fxn(self, module)
152 except:
153 if not is_reload:
154 del sys.modules[fullname]
155 raise
156 _wrap(decorated, fxn)
157 return decorated
158
159
160def _check_name(method):
161 """Decorator to verify that the module being requested matches the one the
162 loader can handle.
163
164 The first argument (self) must define _name which the second argument is
165 comapred against. If the comparison fails then ImportError is raised.
166
167 """
168 def inner(self, name, *args, **kwargs):
169 if self._name != name:
170 raise ImportError("loader cannot handle %s" % name)
171 return method(self, name, *args, **kwargs)
172 _wrap(inner, method)
173 return inner
174
175
176# Finders/loaders #############################################################
177
Brett Cannon5abdc932009-01-22 22:43:07 +0000178class BuiltinImporter:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000179
Brett Cannon5abdc932009-01-22 22:43:07 +0000180 """Meta path loader for built-in modules.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000181
Brett Cannon5abdc932009-01-22 22:43:07 +0000182 All methods are either class or static methods, allowing direct use of the
183 class.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000184
185 """
186
Brett Cannon5abdc932009-01-22 22:43:07 +0000187 @classmethod
188 def find_module(cls, fullname, path=None):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000189 """Try to find the built-in module.
190
191 If 'path' is ever specified then the search is considered a failure.
192
193 """
194 if path is not None:
195 return None
Brett Cannon5abdc932009-01-22 22:43:07 +0000196 return cls if imp.is_builtin(fullname) else None
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000197
Brett Cannon78246b62009-01-25 04:56:30 +0000198 @classmethod
Brett Cannon435aad82009-03-04 16:07:00 +0000199 @set_package
Brett Cannon2cf03a82009-03-10 05:17:37 +0000200 @set_loader
Brett Cannon78246b62009-01-25 04:56:30 +0000201 def load_module(cls, fullname):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000202 """Load a built-in module."""
203 if fullname not in sys.builtin_module_names:
204 raise ImportError("{0} is not a built-in module".format(fullname))
Brett Cannond2e7b332009-02-17 02:45:03 +0000205 is_reload = fullname in sys.modules
206 try:
207 return imp.init_builtin(fullname)
208 except:
209 if not is_reload and fullname in sys.modules:
210 del sys.modules[fullname]
211 raise
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000212
213
Brett Cannon5abdc932009-01-22 22:43:07 +0000214class FrozenImporter:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000215
Brett Cannon5abdc932009-01-22 22:43:07 +0000216 """Meta path class for importing frozen modules.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000217
Brett Cannon5abdc932009-01-22 22:43:07 +0000218 All methods are either class or static method to allow direct use of the
219 class.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000220
Brett Cannon5abdc932009-01-22 22:43:07 +0000221 """
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000222
Brett Cannon5abdc932009-01-22 22:43:07 +0000223 @classmethod
224 def find_module(cls, fullname, path=None):
225 """Find a frozen module."""
226 return cls if imp.is_frozen(fullname) else None
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000227
Brett Cannon5abdc932009-01-22 22:43:07 +0000228 @classmethod
Brett Cannon435aad82009-03-04 16:07:00 +0000229 @set_package
Brett Cannon2cf03a82009-03-10 05:17:37 +0000230 @set_loader
Brett Cannon5abdc932009-01-22 22:43:07 +0000231 def load_module(cls, fullname):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000232 """Load a frozen module."""
Brett Cannon5abdc932009-01-22 22:43:07 +0000233 if cls.find_module(fullname) is None:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000234 raise ImportError("{0} is not a frozen module".format(fullname))
Brett Cannond2e7b332009-02-17 02:45:03 +0000235 is_reload = fullname in sys.modules
236 try:
237 return imp.init_frozen(fullname)
238 except:
239 if not is_reload and fullname in sys.modules:
240 del sys.modules[fullname]
241 raise
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000242
243
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000244def _chained_path_hook(*path_hooks):
Brett Cannon2dee5972009-02-21 03:15:37 +0000245 """Create a closure which sequentially checks path hooks to see which ones
246 (if any) can work with a path."""
247 def path_hook(entry):
248 """Check to see if 'entry' matches any of the enclosed path hooks."""
249 finders = []
250 for hook in path_hooks:
251 try:
252 finder = hook(entry)
253 except ImportError:
254 continue
255 else:
256 finders.append(finder)
257 if not finders:
258 raise ImportError("no finder found")
259 else:
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000260 return _ChainedFinder(*finders)
Brett Cannon2dee5972009-02-21 03:15:37 +0000261
262 return path_hook
263
264
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000265class _ChainedFinder:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000266
267 """Finder that sequentially calls other finders."""
268
Brett Cannon2dee5972009-02-21 03:15:37 +0000269 def __init__(self, *finders):
270 self._finders = finders
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000271
272 def find_module(self, fullname, path=None):
Brett Cannon2dee5972009-02-21 03:15:37 +0000273 for finder in self._finders:
274 result = finder.find_module(fullname, path)
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000275 if result:
276 return result
277 else:
278 return None
279
280
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000281
Brett Cannon2dee5972009-02-21 03:15:37 +0000282class _ExtensionFileLoader:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000283
284 """Loader for extension modules.
285
Brett Cannon2dee5972009-02-21 03:15:37 +0000286 The constructor is designed to work with FileFinder.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000287
288 """
289
290 def __init__(self, name, path, is_pkg):
291 """Initialize the loader.
292
293 If is_pkg is True then an exception is raised as extension modules
294 cannot be the __init__ module for an extension module.
295
296 """
297 self._name = name
298 self._path = path
299 if is_pkg:
300 raise ValueError("extension modules cannot be packages")
301
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000302 @_check_name
Brett Cannon435aad82009-03-04 16:07:00 +0000303 @set_package
Brett Cannon2cf03a82009-03-10 05:17:37 +0000304 @set_loader
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000305 def load_module(self, fullname):
306 """Load an extension module."""
Brett Cannond2e7b332009-02-17 02:45:03 +0000307 is_reload = fullname in sys.modules
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000308 try:
Brett Cannon2cf03a82009-03-10 05:17:37 +0000309 return imp.load_dynamic(fullname, self._path)
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000310 except:
Brett Cannond2e7b332009-02-17 02:45:03 +0000311 if not is_reload and fullname in sys.modules:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000312 del sys.modules[fullname]
313 raise
314
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000315 @_check_name
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000316 def is_package(self, fullname):
317 """Return False as an extension module can never be a package."""
318 return False
319
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000320 @_check_name
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000321 def get_code(self, fullname):
322 """Return None as an extension module cannot create a code object."""
323 return None
324
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000325 @_check_name
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000326 def get_source(self, fullname):
327 """Return None as extension modules have no source code."""
328 return None
329
330
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000331def _suffix_list(suffix_type):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000332 """Return a list of file suffixes based on the imp file type."""
333 return [suffix[0] for suffix in imp.get_suffixes()
334 if suffix[2] == suffix_type]
335
336
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000337
Brett Cannon91cf8822009-02-21 05:41:15 +0000338class PyLoader:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000339
Brett Cannon91cf8822009-02-21 05:41:15 +0000340 """Loader base class for Python source.
341
342 Requires implementing the optional PEP 302 protocols as well as
Brett Cannon94aaf9e2009-02-21 23:12:24 +0000343 source_path.
Brett Cannon91cf8822009-02-21 05:41:15 +0000344
345 """
346
347 @module_for_loader
348 def load_module(self, module):
349 """Load a source module."""
Brett Cannon1014d422009-03-08 20:53:50 +0000350 return self._load_module(module)
Brett Cannon91cf8822009-02-21 05:41:15 +0000351
352 def _load_module(self, module):
353 """Initialize a module from source."""
354 name = module.__name__
Brett Cannon91cf8822009-02-21 05:41:15 +0000355 code_object = self.get_code(module.__name__)
Brett Cannon1014d422009-03-08 20:53:50 +0000356 # __file__ may have been set by the caller, e.g. bytecode path.
Brett Cannon91cf8822009-02-21 05:41:15 +0000357 if not hasattr(module, '__file__'):
Brett Cannon1014d422009-03-08 20:53:50 +0000358 module.__file__ = self.source_path(name)
Brett Cannon91cf8822009-02-21 05:41:15 +0000359 if self.is_package(name):
360 module.__path__ = [module.__file__.rsplit(path_sep, 1)[0]]
361 module.__package__ = module.__name__
362 if not hasattr(module, '__path__'):
363 module.__package__ = module.__package__.rpartition('.')[0]
Brett Cannon1014d422009-03-08 20:53:50 +0000364 module.__loader__ = self
Brett Cannon91cf8822009-02-21 05:41:15 +0000365 exec(code_object, module.__dict__)
366 return module
367
368 def get_code(self, fullname):
369 """Get a code object from source."""
370 source_path = self.source_path(fullname)
Brett Cannon1014d422009-03-08 20:53:50 +0000371 if source_path is None:
372 message = "a source path must exist to load {0}".format(fullname)
373 raise ImportError(message)
Brett Cannon91cf8822009-02-21 05:41:15 +0000374 source = self.get_data(source_path)
375 # Convert to universal newlines.
376 line_endings = b'\n'
377 for index, c in enumerate(source):
378 if c == ord(b'\n'):
379 break
380 elif c == ord(b'\r'):
381 line_endings = b'\r'
382 try:
383 if source[index+1] == ord(b'\n'):
384 line_endings += b'\n'
385 except IndexError:
386 pass
387 break
388 if line_endings != b'\n':
389 source = source.replace(line_endings, b'\n')
390 return compile(source, source_path, 'exec', dont_inherit=True)
391
Brett Cannond43b30b2009-03-10 03:29:23 +0000392 # Never use in implementing import! Imports code within the method.
393 def get_source(self, fullname):
394 """Return the source code for a module.
395
396 self.source_path() and self.get_data() are used to implement this
397 method.
398
399 """
400 path = self.source_path(fullname)
401 if path is None:
402 return None
403 try:
404 source_bytes = self.get_data(path)
405 except IOError:
406 return ImportError("source not available through get_data()")
407 import io
408 import tokenize
409 encoding = tokenize.detect_encoding(io.BytesIO(source_bytes).readline)
410 return source_bytes.decode(encoding[0])
411
Brett Cannon91cf8822009-02-21 05:41:15 +0000412
413class PyPycLoader(PyLoader):
414
415 """Loader base class for Python source and bytecode.
416
417 Requires implementing the methods needed for PyLoader as well as
Brett Cannon94aaf9e2009-02-21 23:12:24 +0000418 source_mtime, bytecode_path, and write_bytecode.
Brett Cannon91cf8822009-02-21 05:41:15 +0000419
420 """
421
422 @module_for_loader
423 def load_module(self, module):
424 """Load a module from source or bytecode."""
425 name = module.__name__
Brett Cannon2a922ed2009-03-09 03:35:50 +0000426 source_path = self.source_path(name)
427 bytecode_path = self.bytecode_path(name)
Brett Cannon29dff8a2009-03-09 00:14:37 +0000428 # get_code can worry about no viable paths existing.
429 module.__file__ = source_path or bytecode_path
Brett Cannon91cf8822009-02-21 05:41:15 +0000430 return self._load_module(module)
431
432 def get_code(self, fullname):
433 """Get a code object from source or bytecode."""
434 # XXX Care enough to make sure this call does not happen if the magic
435 # number is bad?
436 source_timestamp = self.source_mtime(fullname)
437 # Try to use bytecode if it is available.
438 bytecode_path = self.bytecode_path(fullname)
439 if bytecode_path:
440 data = self.get_data(bytecode_path)
441 magic = data[:4]
442 pyc_timestamp = marshal._r_long(data[4:8])
443 bytecode = data[8:]
444 try:
445 # Verify that the magic number is valid.
446 if imp.get_magic() != magic:
447 raise ImportError("bad magic number")
448 # Verify that the bytecode is not stale (only matters when
449 # there is source to fall back on.
450 if source_timestamp:
451 if pyc_timestamp < source_timestamp:
452 raise ImportError("bytecode is stale")
453 except ImportError:
454 # If source is available give it a shot.
455 if source_timestamp is not None:
456 pass
457 else:
458 raise
459 else:
460 # Bytecode seems fine, so try to use it.
461 # XXX If the bytecode is ill-formed, would it be beneficial to
462 # try for using source if available and issue a warning?
463 return marshal.loads(bytecode)
464 elif source_timestamp is None:
465 raise ImportError("no source or bytecode available to create code "
466 "object for {0!r}".format(fullname))
467 # Use the source.
468 code_object = super().get_code(fullname)
469 # Generate bytecode and write it out.
470 if not sys.dont_write_bytecode:
471 data = bytearray(imp.get_magic())
472 data.extend(marshal._w_long(source_timestamp))
473 data.extend(marshal.dumps(code_object))
474 self.write_bytecode(fullname, data)
475 return code_object
476
477
478class PyFileLoader(PyLoader):
479
480 """Load a Python source file."""
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000481
482 def __init__(self, name, path, is_pkg):
483 self._name = name
484 self._is_pkg = is_pkg
485 # Figure out the base path based on whether it was source or bytecode
486 # that was found.
487 try:
488 self._base_path = _path_without_ext(path, imp.PY_SOURCE)
489 except ValueError:
490 self._base_path = _path_without_ext(path, imp.PY_COMPILED)
491
492 def _find_path(self, ext_type):
493 """Find a path from the base path and the specified extension type that
494 exists, returning None if one is not found."""
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000495 for suffix in _suffix_list(ext_type):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000496 path = self._base_path + suffix
497 if _path_exists(path):
498 return path
499 else:
500 return None
501
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000502 @_check_name
Brett Cannon51c50262009-02-01 05:33:17 +0000503 def source_path(self, fullname):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000504 """Return the path to an existing source file for the module, or None
505 if one cannot be found."""
506 # Not a property so that it is easy to override.
507 return self._find_path(imp.PY_SOURCE)
508
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000509 @_check_name
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000510 def get_source(self, fullname):
511 """Return the source for the module as a string.
512
513 Return None if the source is not available. Raise ImportError if the
514 laoder cannot handle the specified module.
515
516 """
Brett Cannon51c50262009-02-01 05:33:17 +0000517 source_path = self._source_path(name)
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000518 if source_path is None:
519 return None
520 import tokenize
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000521 with _closing(_io.FileIO(source_path, 'r')) as file: # Assuming bytes.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000522 encoding, lines = tokenize.detect_encoding(file.readline)
523 # XXX Will fail when passed to compile() if the encoding is
524 # anything other than UTF-8.
525 return open(source_path, encoding=encoding).read()
526
Brett Cannon91cf8822009-02-21 05:41:15 +0000527
528 def get_data(self, path):
529 """Return the data from path as raw bytes."""
Brett Cannon7c9875c2009-03-04 01:10:09 +0000530 return _io.FileIO(path, 'r').read() # Assuming bytes.
Brett Cannon91cf8822009-02-21 05:41:15 +0000531
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000532 @_check_name
Brett Cannon91cf8822009-02-21 05:41:15 +0000533 def is_package(self, fullname):
534 """Return a boolean based on whether the module is a package.
535
536 Raises ImportError (like get_source) if the loader cannot handle the
537 package.
538
539 """
540 return self._is_pkg
541
542
Brett Cannon91cf8822009-02-21 05:41:15 +0000543class PyPycFileLoader(PyPycLoader, PyFileLoader):
544
545 """Load a module from a source or bytecode file."""
546
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000547 @_check_name
Brett Cannon94aaf9e2009-02-21 23:12:24 +0000548 def source_mtime(self, name):
549 """Return the modification time of the source for the specified
550 module."""
551 source_path = self.source_path(name)
552 if not source_path:
553 return None
554 return int(_os.stat(source_path).st_mtime)
555
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000556 @_check_name
Brett Cannon91cf8822009-02-21 05:41:15 +0000557 def bytecode_path(self, fullname):
558 """Return the path to a bytecode file, or None if one does not
559 exist."""
560 # Not a property for easy overriding.
561 return self._find_path(imp.PY_COMPILED)
562
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000563 @_check_name
Brett Cannon776e7012009-02-01 06:07:57 +0000564 def write_bytecode(self, name, data):
565 """Write out 'data' for the specified module, returning a boolean
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000566 signifying if the write-out actually occurred.
567
568 Raises ImportError (just like get_source) if the specified module
569 cannot be handled by the loader.
570
571 """
Brett Cannon51c50262009-02-01 05:33:17 +0000572 bytecode_path = self.bytecode_path(name)
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000573 if not bytecode_path:
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000574 bytecode_path = self._base_path + _suffix_list(imp.PY_COMPILED)[0]
Brett Cannon7c9875c2009-03-04 01:10:09 +0000575 file = _io.FileIO(bytecode_path, 'w') # Assuming bytes.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000576 try:
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000577 with _closing(file) as bytecode_file:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000578 bytecode_file.write(data)
579 return True
580 except IOError as exc:
581 if exc.errno == errno.EACCES:
582 return False
583 else:
584 raise
585
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000586
Brett Cannon2dee5972009-02-21 03:15:37 +0000587class FileFinder:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000588
Brett Cannon2dee5972009-02-21 03:15:37 +0000589 """Base class for file finders.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000590
591 Subclasses are expected to define the following attributes:
592
593 * _suffixes
594 Sequence of file suffixes whose order will be followed.
595
596 * _possible_package
597 True if importer should check for packages.
598
599 * _loader
600 A callable that takes the module name, a file path, and whether
601 the path points to a package and returns a loader for the module
602 found at that path.
603
604 """
605
606 def __init__(self, path_entry):
607 """Initialize an importer for the passed-in sys.path entry (which is
608 assumed to have already been verified as an existing directory).
609
610 Can be used as an entry on sys.path_hook.
611
612 """
Brett Cannon2dee5972009-02-21 03:15:37 +0000613 absolute_path = _path_absolute(path_entry)
614 if not _path_isdir(absolute_path):
615 raise ImportError("only directories are supported")
616 self._path_entry = absolute_path
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000617
618 def find_module(self, fullname, path=None):
Brett Cannon2dee5972009-02-21 03:15:37 +0000619 tail_module = fullname.rpartition('.')[2]
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000620 package_directory = None
621 if self._possible_package:
622 for ext in self._suffixes:
623 package_directory = _path_join(self._path_entry, tail_module)
624 init_filename = '__init__' + ext
625 package_init = _path_join(package_directory, init_filename)
626 if (_path_isfile(package_init) and
627 _case_ok(self._path_entry, tail_module) and
628 _case_ok(package_directory, init_filename)):
629 return self._loader(fullname, package_init, True)
630 for ext in self._suffixes:
631 file_name = tail_module + ext
632 file_path = _path_join(self._path_entry, file_name)
633 if (_path_isfile(file_path) and
634 _case_ok(self._path_entry, file_name)):
635 return self._loader(fullname, file_path, False)
636 else:
637 # Raise a warning if it matches a directory w/o an __init__ file.
638 if (package_directory is not None and
639 _path_isdir(package_directory) and
640 _case_ok(self._path_entry, tail_module)):
641 _warnings.warn("Not importing directory %s: missing __init__"
642 % package_directory, ImportWarning)
643 return None
644
645
Brett Cannon2dee5972009-02-21 03:15:37 +0000646class ExtensionFileFinder(FileFinder):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000647
648 """Importer for extension files."""
649
650 _possible_package = False
651 _loader = _ExtensionFileLoader
652
653 def __init__(self, path_entry):
654 # Assigning to _suffixes here instead of at the class level because
655 # imp is not imported at the time of class creation.
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000656 self._suffixes = _suffix_list(imp.C_EXTENSION)
Brett Cannon2dee5972009-02-21 03:15:37 +0000657 super().__init__(path_entry)
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000658
659
Brett Cannon2dee5972009-02-21 03:15:37 +0000660class PyFileFinder(FileFinder):
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000661
662 """Importer for source/bytecode files."""
663
664 _possible_package = True
Brett Cannon91cf8822009-02-21 05:41:15 +0000665 _loader = PyFileLoader
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000666
667 def __init__(self, path_entry):
668 # Lack of imp during class creation means _suffixes is set here.
669 # Make sure that Python source files are listed first! Needed for an
670 # optimization by the loader.
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000671 self._suffixes = _suffix_list(imp.PY_SOURCE)
Brett Cannon2dee5972009-02-21 03:15:37 +0000672 super().__init__(path_entry)
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000673
674
Brett Cannon4afab6b2009-02-21 03:31:35 +0000675class PyPycFileFinder(PyFileFinder):
676
677 """Finder for source and bytecode files."""
678
Brett Cannon91cf8822009-02-21 05:41:15 +0000679 _loader = PyPycFileLoader
680
Brett Cannon4afab6b2009-02-21 03:31:35 +0000681 def __init__(self, path_entry):
682 super().__init__(path_entry)
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000683 self._suffixes += _suffix_list(imp.PY_COMPILED)
Brett Cannon4afab6b2009-02-21 03:31:35 +0000684
685
Brett Cannonf7e5a8c2009-02-05 02:52:18 +0000686class PathFinder:
Brett Cannon1d376682009-02-02 19:19:36 +0000687
688 """Meta path finder for sys.(path|path_hooks|path_importer_cache)."""
689
Brett Cannonf7e5a8c2009-02-05 02:52:18 +0000690 @classmethod
Brett Cannon32732e32009-02-15 05:48:13 +0000691 def _path_hooks(cls, path, hooks=None):
692 """Search sequence of hooks for a finder for 'path'.
Brett Cannon1d376682009-02-02 19:19:36 +0000693
Brett Cannon32732e32009-02-15 05:48:13 +0000694 If 'hooks' is false then use sys.path_hooks.
Brett Cannon1d376682009-02-02 19:19:36 +0000695
696 """
Brett Cannon32732e32009-02-15 05:48:13 +0000697 if not hooks:
698 hooks = sys.path_hooks
699 for hook in hooks:
Brett Cannon1d376682009-02-02 19:19:36 +0000700 try:
701 return hook(path)
702 except ImportError:
703 continue
704 else:
Brett Cannon32732e32009-02-15 05:48:13 +0000705 raise ImportError("no path hook found for {0}".format(path))
Brett Cannon1d376682009-02-02 19:19:36 +0000706
Brett Cannonf7e5a8c2009-02-05 02:52:18 +0000707 @classmethod
Brett Cannon32732e32009-02-15 05:48:13 +0000708 def _path_importer_cache(cls, path, default=None):
Brett Cannon1d376682009-02-02 19:19:36 +0000709 """Get the finder for the path from sys.path_importer_cache.
710
711 If the path is not in the cache, find the appropriate finder and cache
712 it. If None is cached, get the default finder and cache that
713 (if applicable).
714
715 Because of NullImporter, some finder should be returned. The only
716 explicit fail case is if None is cached but the path cannot be used for
717 the default hook, for which ImportError is raised.
718
719 """
720 try:
Brett Cannonf7e5a8c2009-02-05 02:52:18 +0000721 finder = sys.path_importer_cache[path]
Brett Cannon1d376682009-02-02 19:19:36 +0000722 except KeyError:
Brett Cannonf7e5a8c2009-02-05 02:52:18 +0000723 finder = cls._path_hooks(path)
Brett Cannon1d376682009-02-02 19:19:36 +0000724 sys.path_importer_cache[path] = finder
725 else:
Brett Cannon32732e32009-02-15 05:48:13 +0000726 if finder is None and default:
Brett Cannon1d376682009-02-02 19:19:36 +0000727 # Raises ImportError on failure.
Brett Cannon32732e32009-02-15 05:48:13 +0000728 finder = default(path)
Brett Cannon1d376682009-02-02 19:19:36 +0000729 sys.path_importer_cache[path] = finder
730 return finder
731
Brett Cannonf7e5a8c2009-02-05 02:52:18 +0000732 @classmethod
733 def find_module(cls, fullname, path=None):
Brett Cannon1d376682009-02-02 19:19:36 +0000734 """Find the module on sys.path or 'path'."""
735 if not path:
736 path = sys.path
737 for entry in path:
738 try:
Brett Cannonf7e5a8c2009-02-05 02:52:18 +0000739 finder = cls._path_importer_cache(entry)
Brett Cannon1d376682009-02-02 19:19:36 +0000740 except ImportError:
741 continue
742 loader = finder.find_module(fullname)
743 if loader:
744 return loader
745 else:
746 return None
747
748
Brett Cannonce43ddf2009-03-12 22:28:55 +0000749# Import itself ###############################################################
750
751class _ImportLockContext:
752
753 """Context manager for the import lock."""
754
755 def __enter__(self):
756 """Acquire the import lock."""
757 imp.acquire_lock()
758
759 def __exit__(self, exc_type, exc_value, exc_traceback):
760 """Release the import lock regardless of any raised exceptions."""
761 imp.release_lock()
762
763
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000764_DEFAULT_PATH_HOOK = _chained_path_hook(ExtensionFileFinder, PyPycFileFinder)
Brett Cannon2dee5972009-02-21 03:15:37 +0000765
Brett Cannon32732e32009-02-15 05:48:13 +0000766class _DefaultPathFinder(PathFinder):
767
768 """Subclass of PathFinder that implements implicit semantics for
769 __import__."""
770
Brett Cannon32732e32009-02-15 05:48:13 +0000771 @classmethod
772 def _path_hooks(cls, path):
773 """Search sys.path_hooks as well as implicit path hooks."""
774 try:
775 return super()._path_hooks(path)
776 except ImportError:
Brett Cannon2dee5972009-02-21 03:15:37 +0000777 implicit_hooks = [_DEFAULT_PATH_HOOK, imp.NullImporter]
Brett Cannon32732e32009-02-15 05:48:13 +0000778 return super()._path_hooks(path, implicit_hooks)
779
780 @classmethod
781 def _path_importer_cache(cls, path):
782 """Use the default path hook when None is stored in
783 sys.path_importer_cache."""
Brett Cannon2dee5972009-02-21 03:15:37 +0000784 return super()._path_importer_cache(path, _DEFAULT_PATH_HOOK)
Brett Cannon32732e32009-02-15 05:48:13 +0000785
786
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000787
Brett Cannon32732e32009-02-15 05:48:13 +0000788_IMPLICIT_META_PATH = [BuiltinImporter, FrozenImporter, _DefaultPathFinder]
789
Brett Cannon7f9876c2009-02-06 02:47:33 +0000790def _gcd_import(name, package=None, level=0):
791 """Import and return the module based on its name, the package the call is
792 being made from, and the level adjustment.
793
794 This function represents the greatest common denominator of functionality
Brett Cannon2c318a12009-02-07 01:15:27 +0000795 between import_module and __import__. This includes settting __package__ if
796 the loader did not.
797
Brett Cannon7f9876c2009-02-06 02:47:33 +0000798 """
Brett Cannon2c318a12009-02-07 01:15:27 +0000799 if package:
800 if not hasattr(package, 'rindex'):
801 raise ValueError("__package__ not set to a string")
802 elif package not in sys.modules:
803 msg = ("Parent module {0!r} not loaded, cannot perform relative "
804 "import")
805 raise SystemError(msg.format(package))
806 if not name and level == 0:
807 raise ValueError("Empty module name")
Brett Cannon7f9876c2009-02-06 02:47:33 +0000808 if level > 0:
Brett Cannon2c318a12009-02-07 01:15:27 +0000809 dot = len(package)
Brett Cannon7f9876c2009-02-06 02:47:33 +0000810 for x in range(level, 1, -1):
811 try:
812 dot = package.rindex('.', 0, dot)
Brett Cannon7f9876c2009-02-06 02:47:33 +0000813 except ValueError:
Brett Cannon2c318a12009-02-07 01:15:27 +0000814 raise ValueError("attempted relative import beyond "
815 "top-level package")
816 if name:
817 name = "{0}.{1}".format(package[:dot], name)
818 else:
819 name = package[:dot]
Brett Cannon3eeaa0a2009-03-12 22:07:17 +0000820 with _ImportLockContext():
Brett Cannon7f9876c2009-02-06 02:47:33 +0000821 try:
822 return sys.modules[name]
823 except KeyError:
824 pass
825 parent = name.rpartition('.')[0]
826 path = None
827 if parent:
828 if parent not in sys.modules:
Brett Cannon2c318a12009-02-07 01:15:27 +0000829 _gcd_import(parent)
830 # Backwards-compatibility; be nicer to skip the dict lookup.
831 parent_module = sys.modules[parent]
Brett Cannon7f9876c2009-02-06 02:47:33 +0000832 path = parent_module.__path__
Brett Cannon32732e32009-02-15 05:48:13 +0000833 meta_path = sys.meta_path + _IMPLICIT_META_PATH
Brett Cannon2c318a12009-02-07 01:15:27 +0000834 for finder in meta_path:
Brett Cannon7f9876c2009-02-06 02:47:33 +0000835 loader = finder.find_module(name, path)
Brett Cannon2c318a12009-02-07 01:15:27 +0000836 if loader is not None:
837 loader.load_module(name)
838 break
Brett Cannon7f9876c2009-02-06 02:47:33 +0000839 else:
840 raise ImportError("No module named {0}".format(name))
Brett Cannon2c318a12009-02-07 01:15:27 +0000841 # Backwards-compatibility; be nicer to skip the dict lookup.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000842 module = sys.modules[name]
843 if parent:
Brett Cannon2c318a12009-02-07 01:15:27 +0000844 # Set the module as an attribute on its parent.
845 setattr(parent_module, name.rpartition('.')[2], module)
846 # Set __package__ if the loader did not.
847 if not hasattr(module, '__package__') or module.__package__ is None:
848 # Watch out for what comes out of sys.modules to not be a module,
849 # e.g. an int.
850 try:
851 module.__package__ = module.__name__
852 if not hasattr(module, '__path__'):
853 module.__package__ = module.__package__.rpartition('.')[0]
854 except AttributeError:
855 pass
856 return module
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000857
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000858
Brett Cannon2c318a12009-02-07 01:15:27 +0000859def _import(name, globals={}, locals={}, fromlist=[], level=0):
860 """Import a module.
861
862 The 'globals' argument is used to infer where the import is occuring from
863 to handle relative imports. The 'locals' argument is ignored. The
864 'fromlist' argument specifies what should exist as attributes on the module
865 being imported (e.g. ``from module import <fromlist>``). The 'level'
866 argument represents the package location to import from in a relative
867 import (e.g. ``from ..pkg import mod`` would have a 'level' of 2).
868
869 """
870 if level == 0:
871 module = _gcd_import(name)
872 else:
873 # __package__ is not guaranteed to be defined.
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000874 try:
Brett Cannon2c318a12009-02-07 01:15:27 +0000875 package = globals['__package__']
876 except KeyError:
877 package = globals['__name__']
878 if '__path__' not in globals:
879 package = package.rpartition('.')[0]
880 module = _gcd_import(name, package, level)
881 # The hell that is fromlist ...
882 if not fromlist:
883 # Return up to the first dot in 'name'. This is complicated by the fact
884 # that 'name' may be relative.
885 if level == 0:
886 return sys.modules[name.partition('.')[0]]
887 elif not name:
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000888 return module
Brett Cannon2c318a12009-02-07 01:15:27 +0000889 else:
890 cut_off = len(name) - len(name.partition('.')[0])
891 return sys.modules[module.__name__[:-cut_off]]
892 else:
893 # If a package was imported, try to import stuff from fromlist.
894 if hasattr(module, '__path__'):
895 if '*' in fromlist and hasattr(module, '__all__'):
896 fromlist.remove('*')
897 fromlist.extend(module.__all__)
898 for x in (y for y in fromlist if not hasattr(module,y)):
899 try:
900 _gcd_import('{0}.{1}'.format(module.__name__, x))
901 except ImportError:
902 pass
903 return module
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000904
Brett Cannon23cbd8a2009-01-18 00:24:28 +0000905
906# XXX Eventually replace with a proper __all__ value (i.e., don't expose os
907# replacements but do expose _ExtensionFileLoader, etc. for testing).
908__all__ = [obj for obj in globals().keys() if not obj.startswith('__')]