diff --git a/pep-0302.txt b/pep-0302.txt index 95cb5f79b..56b568aef 100644 --- a/pep-0302.txt +++ b/pep-0302.txt @@ -273,25 +273,33 @@ Specification part 1: The Importer Protocol be a list, but may be empty if __path__ has no further significance to the importer (more on this later). - - It should add an __loader__ attribute to the module, set to the - loader object. This is mostly for introspection, but can be used + - The __loader__ attribute must be set to the loader object. + This is mostly for introspection and reloading, but can be used for importer-specific extras, for example getting data associated with an importer. + - The __package__ attribute [10] must be set. + If the module is a Python module (as opposed to a built-in module or a dynamically loaded extension), it should execute the module's code in the module's global name space (module.__dict__). Here is a minimal pattern for a load_module() method: + # Consider using importlib.util.module_for_loader() to handle + # most of these details for you. def load_module(self, fullname): - ispkg, code = self._get_code(fullname) + code = self.get_code(fullname) + ispkg = self.is_package(fullname) mod = sys.modules.setdefault(fullname, imp.new_module(fullname)) mod.__file__ = "<%s>" % self.__class__.__name__ mod.__loader__ = self if ispkg: mod.__path__ = [] - exec code in mod.__dict__ + mod.__package__ = fullname + else: + mod.__package__ = fullname.rpartition('.')[0] + exec(code, mod.__dict__) return mod @@ -485,24 +493,9 @@ Open Issues importer object, zipimport also adds an attribute "__loader__" to the module, containing the zipimport object used to load the module. If such an approach is used, it is important that client - code takes care not to break if the get_data method (or the - __loader__ attribute) is not available, so it is not clear that - this approach offers a general answer to the problem. - - Requiring loaders to set the module's __loader__ attribute means - that the loader will not get thrown away once the load is complete. - This increases memory usage, and stops loaders from being - lightweight, "throwaway" objects. As loader objects are not - required to offer any useful functionality (any such functionality, - such as the zipimport get_data() method mentioned above, is - optional) it is not clear that the __loader__ attribute will be - helpful, in practice. - - On the other hand, finder objects are mostly permanent, as they - live or are kept alive on sys.meta_path, sys.path_importer_cache, so - for a loader to keep a reference to the importer costs us nothing - extra. Whether loaders will ever need to carry so much independent - state for this to become a real issue is questionable. + code takes care not to break if the get_data method is not available, + so it is not clear that this approach offers a general answer to the + problem. It was suggested on python-dev that it would be useful to be able to receive a list of available modules from an importer and/or a list @@ -586,6 +579,9 @@ References and Footnotes [9] PEP 338: Executing modules as scripts http://www.python.org/dev/peps/pep-0338/ + [10] PEP 366: Main module explicit relative imports + http://www.python.org/dev/peps/pep-0366/ + Copyright