Spec-Zone.ru › Python 3.11

importlib — Реализация импорта

Новое в версии 3.1.

Исходный код: Lib/importlib/__init__.py

Введение

Цель пакета importlib состоит из трёх пунктов.

Во-первых, предоставить реализацию оператора import (и, следовательно, функции __import__()) в исходном коде Python. Это обеспечивает реализацию import, которая является переносимой на любой интерпретатор Python. Это также предоставляет реализацию, которую легче понять, чем реализацию на языке программирования, отличном от Python.

Во-вторых, компоненты для реализации import представлены в этом пакете, что облегчает пользователям создание собственных пользовательских объектов (обобщенно называемых импортером), чтобы они участвовали в процессе импорта.

В-третьих, пакет содержит модули, предоставляющие дополнительную функциональность для управления аспектами пакетов Python:

  • importlib.metadata предоставляет доступ к метаданным из дистрибутивов третьих сторон.
  • importlib.resources предоставляет функции для доступа к некодовым «ресурсам» из пакетов Python.

См. также

Оператор импорта

Справочник языка по оператору import.

Спецификация пакетов

Исходная спецификация пакетов. Некоторые семантические характеристики изменились с момента написания этой документации (например, перенаправление на основе None в sys.modules).

The __import__() function

Оператор import является синтаксическим сахаром для этой функции.

Инициализация пути поиска модуля sys.path

Инициализация sys.path.

PEP 235

Импорт на платформах с регистронезависимым написанием

PEP 263

Определение кодировок исходного кода Python

PEP 302

Новые крючки импорта

PEP 328

Импорт: многострочные и абсолютные/относительные

PEP 366

Явные относительные импорты основного модуля

PEP 420

Неявные пакеты пространств имён

PEP 451

Тип ModuleSpec для системы импорта

PEP 488

Устранение файлов PYO

PEP 489

Многофазная инициализация модулей расширения

PEP 552

Детерминированные pycs

PEP 3120

Использование UTF-8 в качестве кодировки по умолчанию для исходного кода

PEP 3147

Директории хранилища PYC

END_OF_DOCUMENT_MARKER

Функции

importlib.__import__(name, globals=None, locals=None, fromlist=(), level=0)

Реализация встроенной функции __import__().

Примечание

Для программирования импорта модулей следует использовать import_module(), а не эту функцию.

importlib.import_module(name, package=None)

Импортирует модуль. Аргумент name указывает, какой модуль импортировать — в абсолютном или относительном виде (например, pkg.mod или ..mod). Если имя указано относительно, то аргумент package должен содержать имя пакета, который будет использоваться для разрешения имени пакета (например, import_module('..mod', 'pkg.subpkg') импортирует pkg.mod).

Функция import_module() является упрощающей оболочкой над importlib.__import__(). Это означает, что все семантические аспекты функции взяты из importlib.__import__(). Самое важное различие между этими двумя функциями состоит в том, что import_module() возвращает указанный пакет или модуль (например, pkg.mod), а __import__() возвращает верхнеуровневый пакет или модуль (например, pkg).

Если вы динамически импортируете модуль, созданный после начала работы интерпретатора (например, создали файл Python-исходников), вам может потребоваться вызвать invalidate_caches(), чтобы система импорта заметила новый модуль.

Изменено в версии 3.3: Родительские пакеты автоматически импортируются.

importlib.find_loader(name, path=None)

Находит загрузчик модуля, необязательно в указанном пути path. Если модуль находится в sys.modules, то возвращается sys.modules[name].__loader__ (если загрузчик не будет None или не задан, в этом случае поднимается исключение ValueError). В противном случае выполняется поиск с использованием sys.meta_path. Если загрузчик не найден, возвращается None.

У имени с точками его родительские пакеты не импортируются неявно, поскольку это требует их загрузки, а это может быть нежелательно. Чтобы правильно импортировать подмодуль, нужно импортировать все родительские пакеты подмодуля и использовать правильный аргумент для path.

Добавлена в версии 3.3.

Изменено в версии 3.4: Если __loader__ не задан, поднимается исключение ValueError, точно так же, как и когда атрибут установлен в None.

Устарело начиная с версии 3.4: Используйте importlib.util.find_spec() вместо этого.

importlib.invalidate_caches()

Очищает внутренние кэши поисковиков, хранящихся в sys.meta_path. Если поисковик реализует invalidate_caches(), то он будет вызван для выполнения очистки. Эту функцию следует вызывать, если во время выполнения программы созданы/установлены какие-либо модули, чтобы гарантировать, что все поисковики заметят существование нового модуля.

Добавлена в версии 3.3.

Изменено в версии 3.10: Пакеты с пространством имён, созданные/установленные в другом месте sys.path, после того как то же самое пространство имён уже было импортировано, распознаются.

importlib.reload(module)

Перезагружает ранее импортированный модуль module. Аргументом должен быть объект модуля, так что он должен быть успешно импортирован ранее. Это полезно, если вы отредактировали исходный файл модуля с помощью внешнего редактора и хотите попробовать новую версию, не выходя из интерпретатора Python. Значением возврата является объект модуля (который может отличаться, если повторный импорт приводит к размещению другого объекта в sys.modules).

При выполнении reload():

  • Код Python-модуля перекомпилируется, и код модуля на уровне кода выполняется повторно, определяя новый набор объектов, которые привязаны к именам в словаре модуля, повторно используя загрузчик, который изначально загрузил модуль. Функция init модулей расширений не вызывается второй раз.
  • Как и со всеми другими объектами в Python, старые объекты освобождаются только после того, как их счётчики ссылок упадут до нуля.
  • Имена в пространстве имен модуля обновляются, чтобы указывать на любые новые или измененные объекты.
  • Другие ссылки на старые объекты (например, имена, внешние по отношению к модулю) не перенаправляются на новые объекты и должны быть обновлены в каждом пространстве имён, где они встречаются, если это необходимо.

Существует ряд других замечаний:

При перезагрузке модуля его словарь (содержащий глобальные переменные модуля) сохраняется. Переопределения имён заменят старые определения, поэтому, как правило, это не проблема. Если новая версия модуля не определяет имя, которое было определено старой версией, старое определение сохраняется. Эта функция может быть использована для преимущества модуля, если он поддерживает глобальную таблицу или кэш объектов — с помощью оператора try он может проверить наличие таблицы и пропустить её инициализацию при необходимости:

try:
    cache
except NameError:
    cache = {}

В общем случае перезагрузка встроенных или динамически загруженных модулей не очень полезна. Перезагрузка sys, __main__, builtins и других ключевых модулей не рекомендуется. Во многих случаях модули расширений не предназначены для инициализации более одного раза и могут завершиться произвольными способами при перезагрузке.

Если модуль импортирует объекты из другого модуля с использованием from … import …, вызов reload() для другого модуля не переопределяет импортированные из него объекты — один из способов обойти это — повторно выполнить оператор from, другой — использовать import и квалифицированные имена (module.name) вместо этого.

Если модуль создает экземпляры класса, перезагрузка модуля, который определяет класс, не влияет на определения методов экземпляров — они продолжают использовать старое определение класса. То же самое относится к производным классам.

Добавлена в версии 3.4.

Изменено в версии 3.7: Исключение ModuleNotFoundError поднимается, когда перезагружаемый модуль не имеет ModuleSpec.

importlib.abc – Абстрактные базовые классы, связанные с импортом

Исходный код: Lib/importlib/abc.py

Модуль importlib.abc содержит все основные абстрактные базовые классы, используемые модулем import. Также предоставляются некоторые подклассы основных абстрактных базовых классов для помощи в реализации основных ABC.

Иерархия ABC:

object
 +-- Finder (deprecated)
 +-- MetaPathFinder
 +-- PathEntryFinder
 +-- Loader
      +-- ResourceLoader --------+
      +-- InspectLoader          |
           +-- ExecutionLoader --+
                                 +-- FileLoader
                                 +-- SourceLoader
class importlib.abc.Finder

Абстрактный базовый класс, представляющий поисковик.

Устарело начиная с версии 3.3: Используйте MetaPathFinder или PathEntryFinder вместо этого.

abstractmethod find_module(fullname, path=None)

Абстрактный метод для поиска загрузчика для указанного модуля. Первоначально определён в PEP 302, этот метод предназначался для использования в sys.meta_path и в подсистеме импорта на основе путей.

Изменено в версии 3.4: Возвращает None при вызове вместо повышения NotImplementedError.

Устарело начиная с версии 3.10: Реализуйте MetaPathFinder.find_spec() или PathEntryFinder.find_spec() вместо этого.

class importlib.abc.MetaPathFinder

Абстрактный базовый класс, представляющий поисковик мета-пути.

Введено в версии 3.3.

Изменено в версии 3.10: Больше не является подклассом Finder.

find_spec(fullname, path, target=None)

Абстрактный метод для поиска спецификации для указанного модуля. Если это импорт верхнего уровня, path будет None. В противном случае, это поиск подпакета или модуля, и path будет значением __path__ родительского пакета. Если спецификация не найдена, возвращается None. Когда передано, target является объектом модуля, который поисковик может использовать для более точного предположения о том, какую спецификацию вернуть. importlib.util.spec_from_loader() может быть полезным для реализации конкретного MetaPathFinders.

Введено в версии 3.4.

find_module(fullname, path)

Легасный метод для поиска загрузчика для указанного модуля. Если это импорт верхнего уровня, path будет None. В противном случае, это поиск подпакета или модуля, и path будет значением __path__ родительского пакета. Если загрузчик не найден, возвращается None.

Если find_spec() определено, обеспечивается обратная совместимость.

Изменено в версии 3.4: Возвращает None при вызове вместо повышения NotImplementedError. Может использовать find_spec() для обеспечения функциональности.

Устарело начиная с версии 3.4: Используйте find_spec() вместо этого.

invalidate_caches()

Необязательный метод, который, при вызове, должен аннулировать любой внутренний кэш, используемый поисковиком. Используется importlib.invalidate_caches() при аннулировании кэшей всех поисковиков в sys.meta_path.

Изменено в версии 3.4: Возвращает None при вызове вместо NotImplemented.

class importlib.abc.PathEntryFinder

Абстрактный базовый класс, представляющий поисковик по пути. Несмотря на некоторое сходство с MetaPathFinder, PathEntryFinder предназначен для использования только внутри подсистемы импорта на основе пути, предоставляемой importlib.machinery.PathFinder.

Введено в версии 3.3.

Изменено в версии 3.10: Больше не является подклассом Finder.

find_spec(fullname, target=None)

Абстрактный метод для поиска спецификации для указанного модуля. Поисковик будет искать модуль только внутри элемента пути, которому он назначен. Если спецификация не найдена, возвращается None. Переданный target — это объект модуля, который поисковик может использовать для более точного определения, какую спецификацию вернуть. importlib.util.spec_from_loader() может быть полезен для реализации конкретного PathEntryFinders.

Введено в версии 3.4.

find_loader(fullname)

Метод устаревшего типа для поиска загрузчика для указанного модуля. Возвращает пару из 2-х элементов: (loader, portion), где portion — последовательность расположений файловой системы, вносящих вклад в часть пакета имен. Загрузчик может быть None, при этом указывается portion, чтобы указать вклад расположений файловой системы в пакет имен. Пустой список может быть использован для portion, чтобы указать, что загрузчик не является частью пакета имен. Если loader — None, а portion — пустой список, то загрузчик или расположение для пакета имен не найдены (т.е. ничего не найдено для модуля).

Если find_spec() определено, то обеспечивается обратная совместимость.

Изменено в версии 3.4: Возвращает (None, []) вместо повышения NotImplementedError. Использует find_spec() при наличии для обеспечения функциональности.

Устарело начиная с версии 3.4: Используйте find_spec() вместо этого.

find_module(fullname)

Конкретная реализация Finder.find_module(), которая эквивалентна self.find_loader(fullname)[0].

Устарело начиная с версии 3.4: Используйте find_spec() вместо этого.

invalidate_caches()

Необязательный метод, который при вызове должен аннулировать любой внутренний кэш, используемый поисковиком. Используется importlib.machinery.PathFinder.invalidate_caches() при аннулировании кэшей всех кэшированных поисковиков.

class importlib.abc.Loader

Абстрактный базовый класс для загрузчика. См. PEP 302 для точного определения загрузчика.

Загрузчики, которые хотят поддерживать чтение ресурсов, должны реализовать метод get_resource_reader(), как указано в importlib.resources.abc.ResourceReader.

Изменено в версии 3.7: Введён необязательный метод get_resource_reader().

create_module(spec)

Метод, который возвращает объект модуля, который нужно использовать при импорте модуля. Этот метод может вернуть None, указывая, что следует использовать стандартные правила создания модулей.

Введено в версии 3.4.

Изменено в версии 3.6: Этот метод больше не является необязательным, когда определён метод exec_module().

exec_module(module)

Абстрактный метод, который выполняет модуль в собственном пространстве имён при импорте или перезагрузке модуля. Модуль должен быть уже инициализирован, когда вызывается exec_module(). Когда этот метод существует, должен быть определён метод create_module().

Введено в версии 3.4.

Изменено в версии 3.6: Также должен быть определён метод create_module().

load_module(fullname)

Устаревший метод для загрузки модуля. Если модуль не может быть загружен, генерируется исключение ImportError, в противном случае возвращается загруженный модуль.

Если запрашиваемый модуль уже существует в sys.modules, этот модуль должен быть использован и перезагружен. В противном случае загрузчик должен создать новый модуль и вставить его в sys.modules до начала загрузки, чтобы предотвратить рекурсию при импорте. Если загрузчик вставил модуль, а загрузка завершилась ошибкой, он должен удалить его из sys.modules; модули, уже присутствующие в sys.modules до начала работы загрузчика, должны быть оставлены в покое (см. importlib.util.module_for_loader()).

Загрузчик должен установить несколько атрибутов в модуле (обратите внимание, что некоторые из этих атрибутов могут меняться при перезагрузке модуля):

  • __name__

    Полное квалифицированное имя модуля. Оно является '__main__' для выполненного модуля.

  • __file__

    Местоположение, которое использовал загрузчик для загрузки модуля. Например, для модулей, загруженных из файла .py, это имя файла. Оно не устанавливается для всех модулей (например, для встроенных модулей).

  • __cached__

    Имя файла скомпилированной версии кода модуля. Оно не устанавливается для всех модулей (например, для встроенных модулей).

  • __path__

    Список расположений, где будут находиться подмодули пакета. В большинстве случаев это один каталог. Система импорта передаёт этот атрибут методу __import__() и поисковикам так же, как и sys.path, но только для пакета. Он не устанавливается для модулей, не являющихся пакетами, поэтому может использоваться как индикатор того, что модуль является пакетом.

  • __package__

    Полное квалифицированное имя пакета, в котором находится модуль (или пустая строка для модуля верхнего уровня). Если модуль является пакетом, то это то же, что и __name__.

  • __loader__

    Используемый загрузчик для загрузки модуля.

Когда exec_module() доступен, обеспечивается обратная совместимость.

Изменено в версии 3.4: Генерируется исключение ImportError вместо NotImplementedError. Функциональность предоставляется, когда exec_module() доступен.

Устарело начиная с версии 3.4: Рекомендуемый API для загрузки модуля — exec_module() (и create_module()). Загрузчики должны реализовывать его вместо load_module(). Механизм импорта позаботится обо всех других обязанностях load_module(), когда реализован exec_module().

module_repr(module)

Устаревший метод, который, если реализован, вычисляет и возвращает строковое представление данного модуля. По умолчанию модуль будет использовать результат этого метода как уместно.

Введено в версии 3.3.

Изменено в версии 3.4: Стало необязательным вместо абстрактного метода.

Устарело начиная с версии 3.4: Механизм импорта теперь обрабатывает это автоматически.

class importlib.abc.ResourceLoader

Абстрактный базовый класс для загрузчика, который реализует необязательный протокол PEP 302 для загрузки произвольных ресурсов из хранилища.

Устарело начиная с версии 3.7: Этот ABC устарел в пользу поддержки загрузки ресурсов через importlib.resources.abc.ResourceReader.

abstractmethod get_data(path)

Абстрактный метод для возврата байтов данных, расположенных по пути path. Загрузчики, имеющие хранилище в формате файла, позволяющее хранить произвольные данные, могут реализовать этот абстрактный метод для прямого доступа к хранящимся данным. OSError должен быть вызван, если путь path не найден. Ожидается, что path будет построен с использованием атрибута __file__ модуля или элемента из атрибута __path__ пакета.

Изменено в версии 3.4: Генерирует исключение OSError вместо NotImplementedError.

END_OF_DOCUMENT_MARKER
class importlib.abc.InspectLoader

Абстрактный базовый класс для загрузчика, который реализует необязательный протокол PEP 302 для загрузчиков, которые инспектируют модули.

get_code(fullname)

Возвращает объект кода для модуля или None , если у модуля нет объекта кода (например, для встроенного модуля). Вызывает исключение ImportError, если загрузчик не может найти запрашиваемый модуль.

Примечание

Хотя метод имеет реализацию по умолчанию, рекомендуется переопределить его, если это возможно, для повышения производительности.

Изменено в версии 3.4: Больше не абстрактный и предоставлена конкретная реализация.

abstractmethod get_source(fullname)

Абстрактный метод для возвращения исходного кода модуля. Он возвращается в виде текстовой строки с использованием универсальных символов новой строки, преобразуя все распознанные разделители строк в '\n' символы. Возвращает None , если исходный код недоступен (например, для встроенного модуля). Вызывает исключение ImportError, если загрузчик не может найти указанный модуль.

Изменено в версии 3.4: Вызывает исключение ImportError вместо NotImplementedError.

is_package(fullname)

Необязательный метод, который возвращает значение true, если модуль является пакетом, и false в противном случае. Исключение ImportError генерируется, если загрузчик не может найти модуль.

Изменено в версии 3.4: Вызывает исключение ImportError вместо NotImplementedError.

static source_to_code(data, path='<string>')

Создает объект кода из исходного кода Python.

Аргумент data может быть любым, что поддерживает функция compile() (т.е. строка или байты). Аргумент path должен быть «путем» до места происхождения исходного кода, что может быть абстрактным понятием (например, местоположение в файле zip).

С помощью последующего объекта кода можно выполнить его в модуле, выполнив exec(code, module.__dict__).

Новое в версии 3.4.

Изменено в версии 3.5: Метод стал статическим.

exec_module(module)

Реализация Loader.exec_module().

Новое в версии 3.4.

load_module(fullname)

Реализация Loader.load_module().

Устарело начиная с версии 3.4: Используйте exec_module() вместо этого.

class importlib.abc.ExecutionLoader

Абстрактный базовый класс, который наследуется от InspectLoader, который, при реализации, помогает модулю выполняться как скрипт. ABC представляет необязательный протокол PEP 302.

abstractmethod get_filename(fullname)

Абстрактный метод, который должен возвращать значение __file__ для указанного модуля. Если путь недоступен, вызывается исключение ImportError.

Если исходный код доступен, метод должен возвращать путь к исходному файлу, независимо от того, использовался ли байткод для загрузки модуля.

Изменено в версии 3.4: Вызывает исключение ImportError вместо NotImplementedError.

class importlib.abc.FileLoader(fullname, path)

Абстрактный базовый класс, который наследуется от ResourceLoader и ExecutionLoader, предоставляя конкретные реализации ResourceLoader.get_data() и ExecutionLoader.get_filename().

Аргумент fullname — это полное разрешенное имя модуля, который обрабатывает загрузчик. Аргумент path — путь к файлу модуля.

Новое в версии 3.3.

name

Имя модуля, который может обрабатывать загрузчик.

path

Путь к файлу модуля.

load_module(fullname)

Вызывает метод суперкласса load_module().

Устарело начиная с версии 3.4: Используйте Loader.exec_module() вместо этого.

abstractmethod get_filename(fullname)

Возвращает path.

abstractmethod get_data(path)

Считывает path как двоичный файл и возвращает из него байты.

class importlib.abc.SourceLoader

Абстрактный базовый класс для реализации загрузки файлов исходного кода (и необязательно байт-кода). Класс наследуется как от ResourceLoader, так и от ExecutionLoader, требуя реализации:

  • ResourceLoader.get_data()
  • ExecutionLoader.get_filename()

    Должен возвращать только путь к файлу исходного кода; загрузка без исходного кода не поддерживается.

Абстрактные методы, определенные этим классом, предназначены для добавления необязательной поддержки файлов байт-кода. Не реализация этих необязательных методов (или их вызов с возбуждением NotImplementedError) заставляет загрузчик работать только с исходным кодом. Реализация методов позволяет загрузчику работать с файлами исходного кода и байт-кода; она не допускает загрузки без исходного кода, где предоставлен только байт-код. Файлы байт-кода являются оптимизацией для ускорения загрузки, устраняя этап анализа компилятора Python, поэтому не предоставляется API, специфичный для байт-кода.

path_stats(path)

Необязательный абстрактный метод, возвращающий dict с метаданными о заданном пути. Поддерживаемые ключи словаря:

  • 'mtime' (обязательно): целое или дробное число, представляющее время последнего изменения исходного кода;
  • 'size' (необязательно): размер исходного кода в байтах.

Любые другие ключи в словаре игнорируются, чтобы позволить будущие расширения. Если путь не может быть обработан, возбуждается OSError.

Введено в версии 3.3.

Изменено в версии 3.4: Возбуждается OSError вместо NotImplementedError.

path_mtime(path)

Необязательный абстрактный метод, возвращающий время последнего изменения для заданного пути.

Устарело начиная с версии 3.3: Этот метод устарел в пользу path_stats(). Необязательно его реализовывать, но он по-прежнему доступен для совместимости. Возбуждается OSError, если путь не может быть обработан.

Изменено в версии 3.4: Возбуждается OSError вместо NotImplementedError.

set_data(path, data)

Необязательный абстрактный метод, записывающий указанные байты в файл по пути. Любые промежуточные директории, которых нет, создаются автоматически.

При неудачной записи по пути из-за того, что путь только для чтения (errno.EACCES/PermissionError), исключение не распространяется.

Изменено в версии 3.4: Больше не возбуждает NotImplementedError при вызове.

get_code(fullname)

Конкретная реализация InspectLoader.get_code().

exec_module(module)

Конкретная реализация Loader.exec_module().

Введено в версии 3.4.

load_module(fullname)

Конкретная реализация Loader.load_module().

Устарело начиная с версии 3.4: Используйте exec_module() вместо этого.

get_source(fullname)

Конкретная реализация InspectLoader.get_source().

is_package(fullname)

Конкретная реализация InspectLoader.is_package(). Модуль определяется как пакет, если его путь к файлу (как указано в ExecutionLoader.get_filename()) — это файл с именем __init__ после удаления расширения и само имя модуля не заканчивается на __init__.

importlib.machinery – Импортеры и обработчики путей

Исходный код: Lib/importlib/machinery.py

Этот модуль содержит различные объекты, которые помогают import находить и загружать модули.

importlib.machinery.SOURCE_SUFFIXES

Список строк, представляющих распознанные расширения файлов для исходных модулей.

Введено в версии 3.3.

importlib.machinery.DEBUG_BYTECODE_SUFFIXES

Список строк, представляющих расширения файлов для неоптимизированных модулей байткода.

Введено в версии 3.3.

Устарело начиная с версии 3.5: Используйте BYTECODE_SUFFIXES вместо этого.

importlib.machinery.OPTIMIZED_BYTECODE_SUFFIXES

Список строк, представляющих расширения файлов для оптимизированных модулей байткода.

Введено в версии 3.3.

Устарело начиная с версии 3.5: Используйте BYTECODE_SUFFIXES вместо этого.

importlib.machinery.BYTECODE_SUFFIXES

Список строк, представляющих распознанные расширения файлов для модулей байткода (включая ведущую точку).

Введено в версии 3.3.

Изменено в версии 3.5: Значение больше не зависит от __debug__.

importlib.machinery.EXTENSION_SUFFIXES

Список строк, представляющих распознанные расширения файлов для модулей расширений.

Введено в версии 3.3.

importlib.machinery.all_suffixes()

Возвращает комбинированный список строк, представляющих все расширения файлов для модулей, распознаваемых стандартным механизмом импорта. Это вспомогательная функция для кода, которому просто нужно знать, может ли путь к файловой системе потенциально ссылаться на модуль, не требуя никаких деталей о типе модуля (например, inspect.getmodulename()).

Введено в версии 3.3.

class importlib.machinery.BuiltinImporter

Импортер для встроенных модулей. Все известные встроенные модули перечислены в sys.builtin_module_names. Этот класс реализует ABC importlib.abc.MetaPathFinder и importlib.abc.InspectLoader.

Этот класс определяет только методы класса, чтобы избежать необходимости в создании экземпляра.

Изменено в версии 3.5: В рамках PEP 489 встроенный импортер теперь реализует Loader.create_module() и Loader.exec_module()

class importlib.machinery.FrozenImporter

Импортер для замороженных модулей. Этот класс реализует ABC importlib.abc.MetaPathFinder и importlib.abc.InspectLoader.

Этот класс определяет только методы класса, чтобы избежать необходимости в создании экземпляра.

Изменено в версии 3.4: Получил методы create_module() и exec_module().

class importlib.machinery.WindowsRegistryFinder

Поиск модулей, объявленных в реестре Windows. Этот класс реализует ABC importlib.abc.MetaPathFinder.

Этот класс определяет только методы класса, чтобы избежать необходимости в создании экземпляра.

Введено в версии 3.3.

Устарело начиная с версии 3.6: Используйте настройки site вместо этого. Будущие версии Python могут не включать этот поиск по умолчанию.

class importlib.machinery.PathFinder

Поиск по sys.path и атрибутам пакета __path__. Этот класс реализует ABC importlib.abc.MetaPathFinder.

Этот класс определяет только методы класса, чтобы избежать необходимости в создании экземпляра.

classmethod find_spec(fullname, path=None, target=None)

Метод класса, который пытается найти спецификацию модуля, указанного в fullname, в sys.path или, если определено, в path. Для каждой проверяемой записи пути проверяется sys.path_importer_cache. Если найдено ненулевое значение, то оно используется в качестве поисковика по записи пути для поиска искомого модуля. Если запись не найдена в sys.path_importer_cache, то ищется поисковик для записи пути в sys.path_hooks и, если найден, сохраняется в sys.path_importer_cache вместе с запросом о модуле. Если поисковик не найден ни разу, то None хранится в кэше и возвращается.

Введено в версии 3.4.

Изменено в версии 3.5: Если текущая рабочая директория (представленная пустой строкой) больше не допустима, то возвращается None , но в sys.path_importer_cache ничего не кешируется.

classmethod find_module(fullname, path=None)

Устаревшая оболочка вокруг find_spec().

Устарело начиная с версии 3.4: Используйте find_spec() вместо этого.

classmethod invalidate_caches()

Вызывает importlib.abc.PathEntryFinder.invalidate_caches() для всех поисковиков, хранящихся в sys.path_importer_cache, которые определяют этот метод. В противном случае записи в sys.path_importer_cache, установленные в None, удаляются.

Изменено в версии 3.7: Записи None в sys.path_importer_cache удаляются.

Изменено в версии 3.4: Вызывает объекты в sys.path_hooks с текущей рабочей директорией для '' (т.е. пустой строкой).

END_OF_DOCUMENT_MARKER
class importlib.machinery.FileFinder(path, *loader_details)

Конкретная реализация importlib.abc.PathEntryFinder, кэширующая результаты из файловой системы.

Аргумент path — это директория, за поиск в которой отвечает данный поиск.

Аргумент loader_details — это переменное число кортежей из двух элементов, каждый из которых содержит загрузчик и последовательность расширений файлов, распознаваемых этим загрузчиком. Ожидается, что загрузчики будут вызываемыми объектами, принимающими два аргумента: имя модуля и путь к найденному файлу.

Поиск будет кэшировать содержимое директории по мере необходимости, используя вызовы stat для каждого поиска модуля, чтобы проверить, не устарел ли кэш. Поскольку устаревание кэша зависит от гранулярности информации операционной системы о состоянии файловой системы, существует потенциальная проблема гонки при поиске модуля, создании нового файла и последующем поиске модуля, который представляет этот новый файл. Если операции выполняются достаточно быстро, чтобы уместиться в гранулярности вызовов stat, поиск модуля завершится неудачей. Чтобы предотвратить это, при динамическом создании модуля, убедитесь, что вы вызываете importlib.invalidate_caches().

Добавлена в версии 3.3.

path

Путь, по которому будет производиться поиск.

find_spec(fullname, target=None)

Попытка найти спецификацию для обработки fullname в пределах path.

Добавлена в версии 3.4.

find_loader(fullname)

Попытка найти загрузчик для обработки fullname в пределах path.

Устарело начиная с версии 3.10: Используйте find_spec() вместо этого.

invalidate_caches()

Очистка внутреннего кэша.

classmethod path_hook(*loader_details)

Метод класса, возвращающий замыкание для использования с sys.path_hooks. Экземпляр FileFinder возвращается замыканием, используя аргумент path, переданный замыканию непосредственно, и loader_details косвенно.

Если аргумент замыкания не является существующей директорией, будет поднято исключение ImportError.

class importlib.machinery.SourceFileLoader(fullname, path)

Конкретная реализация importlib.abc.SourceLoader путём наследования от importlib.abc.FileLoader и предоставления конкретных реализаций других методов.

Добавлена в версии 3.3.

name

Имя модуля, который будет обрабатывать этот загрузчик.

path

Путь к исходному файлу.

is_package(fullname)

Возвращает True если path кажется, что предназначен для пакета.

path_stats(path)

Конкретная реализация importlib.abc.SourceLoader.path_stats().

set_data(path, data)

Конкретная реализация importlib.abc.SourceLoader.set_data().

load_module(name=None)

Конкретная реализация importlib.abc.Loader.load_module(), где указание имени загружаемого модуля является необязательным.

Устарело начиная с версии 3.6: Используйте importlib.abc.Loader.exec_module() вместо этого.

class importlib.machinery.SourcelessFileLoader(fullname, path)

Конкретная реализация importlib.abc.FileLoader, которая может импортировать байт-кодовые файлы (т. е. файлы исходного кода отсутствуют).

Обратите внимание, что прямое использование байт-кодовых файлов (и, следовательно, не файлов исходного кода) препятствует использованию ваших модулей всеми реализациями Python или новыми версиями Python, которые изменяют формат байт-кода.

Добавлена в версии 3.3.

name

Имя модуля, который будет обрабатывать данный загрузчик.

path

Путь к байт-кодовому файлу.

is_package(fullname)

Определяет, является ли модуль пакетом, основываясь на path.

get_code(fullname)

Возвращает объект кода для name, созданный из path.

get_source(fullname)

Возвращает None так как байт-кодовые файлы не имеют исходного кода при использовании этого загрузчика.

load_module(name=None)

Конкретная реализация importlib.abc.Loader.load_module(), где указание имени загружаемого модуля является необязательным.

Устарело начиная с версии 3.6: Используйте importlib.abc.Loader.exec_module() вместо этого.

class importlib.machinery.ExtensionFileLoader(fullname, path)

Конкретная реализация importlib.abc.ExecutionLoader для модулей расширения.

Аргумент fullname указывает имя модуля, который должен поддерживаться загрузчиком. Аргумент path — путь к файлу модуля расширения.

Добавлена в версии 3.3.

name

Имя модуля, поддерживаемого загрузчиком.

path

Путь к модулю расширения.

create_module(spec)

Создаёт объект модуля из заданного описания в соответствии с PEP 489.

Добавлена в версии 3.5.

exec_module(module)

Инициализирует заданный объект модуля в соответствии с PEP 489.

Добавлена в версии 3.5.

is_package(fullname)

Возвращает True, если путь к файлу указывает на пакетный __init__ модуль на основе EXTENSION_SUFFIXES.

get_code(fullname)

Возвращает None, так как модули расширения не имеют объекта кода.

get_source(fullname)

Возвращает None, так как модули расширения не имеют исходного кода.

get_filename(fullname)

Возвращает path.

Добавлена в версии 3.4.

class importlib.machinery.NamespaceLoader(name, path, path_finder)

Конкретная реализация importlib.abc.InspectLoader для пакетов пространств имён. Это псевдоним для закрытого класса и используется только для получения доступа к атрибуту __loader__ пакетов пространств имён:

>>> from importlib.machinery import NamespaceLoader
>>> import my_namespace
>>> isinstance(my_namespace.__loader__, NamespaceLoader)
True
>>> import importlib.abc
>>> isinstance(my_namespace.__loader__, importlib.abc.Loader)
True

Добавлена в версии 3.11.

class importlib.machinery.ModuleSpec(name, loader, *, origin=None, loader_state=None, is_package=None)

Спецификация для состояния модуля, связанного с системой импорта. Обычно она предоставляется как атрибут модуля __spec__. В описаниях ниже, имена в скобках указывают соответствующие атрибуты, доступные непосредственно в объекте модуля, например module.__spec__.origin == module.__file__. Однако следует отметить, что, хотя значения обычно эквивалентны, они могут отличаться, так как нет синхронизации между двумя объектами. Например, можно обновить атрибут модуля __file__ во время выполнения, и это не будет автоматически отражено в атрибуте модуля __spec__.origin, и наоборот.

Добавлена в версии 3.4.

name

(__name__)

Полное квалифицированное имя модуля. Найденный объект должен всегда устанавливать этот атрибут в непустую строку.

loader

(__loader__)

Загрузчик, используемый для загрузки модуля. Найденный объект должен всегда установить этот атрибут.

origin

(__file__)

Местоположение, которое должен использовать загрузчик для загрузки модуля. Например, для модулей, загруженных из файла .py, это имя файла. Найденный объект должен всегда установить этот атрибут в осмысленное значение для использования загрузчиком. В редких случаях, когда такого места нет (например, для пакетов пространств имен), оно должно устанавливаться в None.

submodule_search_locations

(__path__)

Список расположений, где будут находиться подмодули пакета. В большинстве случаев это один каталог. Найденный объект должен устанавливать этот атрибут в список, даже в пустой, чтобы указать системе импорта, что модуль является пакетом. Для модулей, которые не являются пакетами, он должен быть установлен в None. Для пакетов пространств имён он автоматически устанавливается в специальный объект.

loader_state

Найденный объект может установить этот атрибут в объект, содержащий дополнительные данные, специфичные для модуля, используемые при загрузке модуля. В противном случае он должен устанавливаться в None.

cached

(__cached__)

Имя файла скомпилированной версии кода модуля. Найденный объект должен всегда устанавливать этот атрибут, но он может быть None для модулей, которым не нужно хранить скомпилированный код.

parent

(__package__)

(Только для чтения) Полное квалифицированное имя пакета, в котором находится модуль (или пустая строка для модуля верхнего уровня). Если модуль является пакетом, то это то же самое, что и name.

has_location
True if the spec’s origin refers to a loadable location,

False в противном случае. Это значение влияет на то, как интерпретируется origin и как заполняется атрибут модуля __file__.

importlib.util – Утилитарный код для импортеров

Исходный код: Lib/importlib/util.py

Этот модуль содержит различные объекты, которые помогают в построении импортера.

importlib.util.MAGIC_NUMBER

Байты, представляющие номер версии байткода. Если вам нужна помощь с загрузкой/записью байткода, обратитесь к importlib.abc.SourceLoader.

Добавлена в версии 3.4.

importlib.util.cache_from_source(path, debug_override=None, *, optimization=None)

Возвращает путь к файлу с байткодом, ассоциированный с исходным путем path, согласно PEP 3147/PEP 488. Например, если path равен /foo/bar/baz.py , то возвращаемое значение будет /foo/bar/__pycache__/baz.cpython-32.pyc для Python 3.2. Строка cpython-32 взята из текущего магического тега (см. get_tag(); если sys.implementation.cache_tag не определено, то будет поднято исключение NotImplementedError).

Параметр optimization используется для указания уровня оптимизации файла байткода. Пустая строка обозначает отсутствие оптимизации, поэтому /foo/bar/baz.py с optimization равным '' приведет к пути байткода /foo/bar/__pycache__/baz.cpython-32.pyc. None приводит к использованию уровня оптимизации интерпретатора. Любое другое значение используется в виде строки, так /foo/bar/baz.py с optimization равным 2 приведёт к пути байткода /foo/bar/__pycache__/baz.cpython-32.opt-2.pyc. Строковое представление optimization может содержать только символы латинского алфавита и цифры; в противном случае будет поднято исключение ValueError.

Параметр debug_override устарел и может быть использован для переопределения системного значения для __debug__. Значение True эквивалентно установке optimization в пустую строку. Значение False эквивалентно установке optimization в 1. Если оба параметра debug_override и optimization не None, то будет поднято исключение TypeError.

Добавлена в версии 3.4.

Изменено в версии 3.5: Добавлен параметр optimization, параметр debug_override устарел.

Изменено в версии 3.6: Принимает объект-путь.

importlib.util.source_from_cache(path)

Учитывая путь path к имени файла PEP 3147, возвращает ассоциированный путь к файлу исходного кода. Например, если path равен /foo/bar/__pycache__/baz.cpython-32.pyc , возвращаемый путь будет /foo/bar/baz.py. path может не существовать, однако, если он не соответствует формату PEP 3147 или PEP 488, будет поднято исключение ValueError. Если sys.implementation.cache_tag не определено, будет поднято исключение NotImplementedError.

Добавлена в версии 3.4.

Изменено в версии 3.6: Принимает объект-путь.

importlib.util.decode_source(source_bytes)

Декодирует заданные байты, представляющие исходный код, и возвращает его как строку с универсальными разделителями строк (как требуется в importlib.abc.InspectLoader.get_source()).

Добавлена в версии 3.4.

importlib.util.resolve_name(name, package)

Преобразует относительное имя модуля в абсолютное.

Если у name нет ведущих точек, то возвращается просто name. Это позволяет использовать, например, importlib.util.resolve_name('sys', __spec__.parent) без проверки необходимости аргумента package.

Если name является относительным именем модуля, но package имеет ложное значение (например, None или пустая строка), то поднимается исключение ImportError. ImportError также поднимается, если относительное имя выходит за пределы содержащего пакета (например, запрос ..bacon изнутри пакета spam).

Добавлена в версии 3.3.

Изменено в версии 3.9: Для повышения согласованности с операторами импорта, для неверных попыток относительного импорта будет подниматься исключение ImportError вместо ValueError.

importlib.util.find_spec(name, package=None)

Находит спецификацию (спецификацию) модуля, необязательно относительно указанного имени пакета package. Если модуль находится в sys.modules, то возвращается sys.modules[name].__spec__ (за исключением случаев, когда спецификация будет None или не установлена, в этом случае поднимается исключение ValueError). В противном случае выполняется поиск с использованием sys.meta_path. None возвращается, если спецификация не найдена.

Если name относится к подмодулю (содержит точку), родительский модуль импортируется автоматически.

name и package работают так же, как и для import_module().

Добавлена в версии 3.4.

Изменено в версии 3.7: Поднимает исключение ModuleNotFoundError вместо AttributeError, если package фактически не является пакетом (т.е. не имеет атрибута __path__).

importlib.util.module_from_spec(spec)

Создаёт новый модуль на основе spec и spec.loader.create_module.

Если spec.loader.create_module не возвращает None, то любые ранее существовавшие атрибуты не будут сброшены. Также не будет поднято исключение AttributeError, если оно возникнет при доступе к spec или при установке атрибута в модуле.

Эта функция предпочтительнее использования types.ModuleType для создания нового модуля, так как spec используется для установки по возможности всех контролируемых импортом атрибутов в модуле.

Добавлена в версии 3.5.

END_OF_DOCUMENT_MARKER
@importlib.util.module_for_loader

Декоратор для importlib.abc.Loader.load_module(), который обрабатывает выбор правильного объекта модуля для загрузки. Ожидается, что декорированный метод будет принимать два позиционных аргумента (например, load_module(self, module)), при этом второй аргумент будет объектом модуля, используемым загрузчиком. Обратите внимание, что декоратор не будет работать со статическими методами из-за предположения о двух аргументах.

Декорированный метод будет принимать имя загружаемого модуля, как ожидается для загрузчика. Если модуль не найден в sys.modules, то создаётся новый. Независимо от источника модуля, __loader__ устанавливается в self, а __package__ устанавливается на основе того, что возвращает importlib.abc.InspectLoader.is_package() (если доступно). Эти атрибуты устанавливаются безусловно для поддержки перезагрузки.

Если декорированный метод вызывает исключение, а модуль был добавлен в sys.modules, то модуль будет удалён, чтобы предотвратить оставление частично инициализированного модуля в sys.modules. Если модуль уже присутствует в sys.modules, он остаётся без изменений.

Изменено в версии 3.3: __loader__ и __package__ автоматически устанавливаются (если это возможно).

Изменено в версии 3.4: Устанавливаются __name__, __loader__ и __package__ безусловно для поддержки перезагрузки.

Устарело начиная с версии 3.4: Механизм импорта теперь напрямую выполняет все функции, предоставляемые этой функцией.

@importlib.util.set_loader

Декоратор для importlib.abc.Loader.load_module(), который устанавливает атрибут __loader__ возвращённого модуля. Если атрибут уже установлен, декоратор ничего не делает. Предполагается, что первый позиционный аргумент обернутого метода (т.е. self) — это значение, которое должно быть установлено для __loader__.

Изменено в версии 3.4: Устанавливает __loader__ если установлено None, как если бы атрибут не существовал.

Устарело начиная с версии 3.4: Механизм импорта теперь выполняет это автоматически.

@importlib.util.set_package

Декоратор для importlib.abc.Loader.load_module(), который устанавливает атрибут __package__ возвращённого модуля. Если __package__ установлен и имеет значение, отличное от None, он не будет изменён.

Устарело начиная с версии 3.4: Механизм импорта теперь выполняет это автоматически.

importlib.util.spec_from_loader(name, loader, *, origin=None, is_package=None)

Функция-фабрика для создания экземпляра ModuleSpec на основе загрузчика. Параметры имеют то же значение, что и для ModuleSpec. Функция использует доступные API загрузчика, такие как InspectLoader.is_package(), чтобы заполнить любые отсутствующие данные в спецификации.

Добавлена в версии 3.4.

importlib.util.spec_from_file_location(name, location, *, loader=None, submodule_search_locations=None)

Функция-фабрика для создания экземпляра ModuleSpec на основе пути к файлу. Отсутствующие данные в спецификации будут заполнены путём использования API загрузчика и предположения, что модуль будет основан на файле.

Добавлена в версии 3.4.

Изменено в версии 3.6: Принимает объект-путь.

importlib.util.source_hash(source_bytes)

Возвращает хеш source_bytes в виде байтов. Файл модуля с хешем .pyc встраивает хеш source_hash() содержимого соответствующего исходного файла в свой заголовок.

Добавлена в версии 3.7.

class importlib.util.LazyLoader(loader)

Класс, откладывающий выполнение загрузчика модуля до тех пор, пока к модулю не будет обращено внимание.

Этот класс только работает с загрузчиками, которые определяют exec_module() для управления типом модуля, необходимым для модуля. По тем же причинам метод загрузчика create_module() должен возвращать None или тип, для которого его атрибут __class__ может быть изменён, а также не использовать __slots__. Наконец, модули, которые подменяют объект, помещённый в sys.modules, не будут работать, так как нет способа безопасно заменить ссылки на модуль во всём интерпретаторе; в случае такой подмены генерируется ValueError.

Примечание

Для проектов, где время запуска имеет решающее значение, этот класс позволяет потенциально минимизировать стоимость загрузки модуля, если он никогда не используется. Для проектов, где время запуска не имеет решающего значения, использование этого класса крайне нежелательно, так как сообщения об ошибках, возникающие во время загрузки, откладываются и, следовательно, появляются вне контекста.

Добавлена в версии 3.5.

Изменено в версии 3.6: Начал вызывать create_module(), убрал предупреждение о совместимости для importlib.machinery.BuiltinImporter и importlib.machinery.ExtensionFileLoader.

classmethod factory(loader)

Метод класса, который возвращает вызываемый объект, создающий ленивый загрузчик. Это предназначено для ситуаций, когда загрузчик передаётся по классу, а не по экземпляру.

suffixes = importlib.machinery.SOURCE_SUFFIXES
loader = importlib.machinery.SourceFileLoader
lazy_loader = importlib.util.LazyLoader.factory(loader)
finder = importlib.machinery.FileFinder(path, (lazy_loader, suffixes))

Примеры

Программный импорт

Для программного импорта модуля используйте importlib.import_module().

import importlib

itertools = importlib.import_module('itertools')

Проверка возможности импорта модуля

Если вам нужно узнать, можно ли импортировать модуль, не выполняя сам импорт, используйте importlib.util.find_spec().

Обратите внимание, что если name является подмодулем (содержит точку), importlib.util.find_spec() импортирует родительский модуль.

import importlib.util
import sys

# For illustrative purposes.
name = 'itertools'

if name in sys.modules:
    print(f"{name!r} already in sys.modules")
elif (spec := importlib.util.find_spec(name)) is not None:
    # If you chose to perform the actual import ...
    module = importlib.util.module_from_spec(spec)
    sys.modules[name] = module
    spec.loader.exec_module(module)
    print(f"{name!r} has been imported")
else:
    print(f"can't find the {name!r} module")

Импорт исходного файла напрямую

Для импорта Python-исходного файла напрямую используйте следующий рецепт:

import importlib.util
import sys

# For illustrative purposes.
import tokenize
file_path = tokenize.__file__
module_name = tokenize.__name__

spec = importlib.util.spec_from_file_location(module_name, file_path)
module = importlib.util.module_from_spec(spec)
sys.modules[module_name] = module
spec.loader.exec_module(module)

Реализация ленивых импортов

В примере ниже показано, как реализовать ленивые импорты:

>>> import importlib.util
>>> import sys
>>> def lazy_import(name):
...     spec = importlib.util.find_spec(name)
...     loader = importlib.util.LazyLoader(spec.loader)
...     spec.loader = loader
...     module = importlib.util.module_from_spec(spec)
...     sys.modules[name] = module
...     loader.exec_module(module)
...     return module
...
>>> lazy_typing = lazy_import("typing")
>>> #lazy_typing is a real module object,
>>> #but it is not loaded in memory yet.
>>> lazy_typing.TYPE_CHECKING
False

Настройка импортера

Для глубокой настройки импорта, как правило, нужно реализовать импортер. Это означает управление как поисковиком, так и загрузчиком. Для поисковиков есть два варианта в зависимости от ваших потребностей: поисковик мета-пути или поисковик элемента пути. Первый — то, что вы помещаете в sys.meta_path, а второй — то, что вы создаёте с помощью обработчика элемента пути в sys.path_hooks, который работает с записями в sys.path, чтобы потенциально создать поисковик. В этом примере показано, как зарегистрировать собственные импортеры, чтобы импорт использовал их (для создания собственного импортера, прочитайте документацию по соответствующим классам, определённым в этом пакете):

import importlib.machinery
import sys

# For illustrative purposes only.
SpamMetaPathFinder = importlib.machinery.PathFinder
SpamPathEntryFinder = importlib.machinery.FileFinder
loader_details = (importlib.machinery.SourceFileLoader,
                  importlib.machinery.SOURCE_SUFFIXES)

# Setting up a meta path finder.
# Make sure to put the finder in the proper location in the list in terms of
# priority.
sys.meta_path.append(SpamMetaPathFinder)

# Setting up a path entry finder.
# Make sure to put the path hook in the proper location in the list in terms
# of priority.
sys.path_hooks.append(SpamPathEntryFinder.path_hook(loader_details))

Приближение importlib.import_module()

Сам импорт реализован на языке Python, что позволяет экспонировать большую часть механизма импорта через importlib. Следующее помогает проиллюстрировать различные API, которые предоставляет importlib, предоставляя приблизительную реализацию importlib.import_module():

import importlib.util
import sys

def import_module(name, package=None):
    """An approximate implementation of import."""
    absolute_name = importlib.util.resolve_name(name, package)
    try:
        return sys.modules[absolute_name]
    except KeyError:
        pass

    path = None
    if '.' in absolute_name:
        parent_name, _, child_name = absolute_name.rpartition('.')
        parent_module = import_module(parent_name)
        path = parent_module.__spec__.submodule_search_locations
    for finder in sys.meta_path:
        spec = finder.find_spec(absolute_name, path)
        if spec is not None:
            break
    else:
        msg = f'No module named {absolute_name!r}'
        raise ModuleNotFoundError(msg, name=absolute_name)
    module = importlib.util.module_from_spec(spec)
    sys.modules[absolute_name] = module
    spec.loader.exec_module(module)
    if path is not None:
        setattr(parent_module, child_name, module)
    return module

© 2001–2023 Python Software Foundation
Licensed under the PSF License.
https://docs.python.org/3.11/library/importlib.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API