gh-93610: Improve docs for importlib.resources (#93611)

Co-authored-by: Adam Turner <9087854+AA-Turner@users.noreply.github.com>
Co-authored-by: Stanley <46876382+slateny@users.noreply.github.com>
Co-authored-by: Łukasz Langa <lukasz@langa.pl>
This commit is contained in:
Petr Viktorin 2022-07-25 18:16:17 +02:00 committed by GitHub
parent a566912049
commit ccd7c7a0bd
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 328 additions and 281 deletions

View file

@ -1,3 +1,15 @@
:mod:`importlib.resources.abc` -- Abstract base classes for resources
---------------------------------------------------------------------
.. module:: importlib.resources.abc
:synopsis: Abstract base classes for resources
**Source code:** :source:`Lib/importlib/resources/abc.py`
--------------
.. versionadded:: 3.11
.. class:: ResourceReader
*Superseded by TraversableResources*
@ -72,251 +84,6 @@
The abstract method returns an iterable of no items.
.. class:: ResourceLoader
An abstract base class for a :term:`loader` which implements the optional
:pep:`302` protocol for loading arbitrary resources from the storage
back-end.
.. deprecated:: 3.7
This ABC is deprecated in favour of supporting resource loading
through :class:`importlib.abc.ResourceReader`.
.. abstractmethod:: get_data(path)
An abstract method to return the bytes for the data located at *path*.
Loaders that have a file-like storage back-end
that allows storing arbitrary data
can implement this abstract method to give direct access
to the data stored. :exc:`OSError` is to be raised if the *path* cannot
be found. The *path* is expected to be constructed using a module's
:attr:`__file__` attribute or an item from a package's :attr:`__path__`.
.. versionchanged:: 3.4
Raises :exc:`OSError` instead of :exc:`NotImplementedError`.
.. class:: InspectLoader
An abstract base class for a :term:`loader` which implements the optional
:pep:`302` protocol for loaders that inspect modules.
.. method:: get_code(fullname)
Return the code object for a module, or ``None`` if the module does not
have a code object (as would be the case, for example, for a built-in
module). Raise an :exc:`ImportError` if loader cannot find the
requested module.
.. note::
While the method has a default implementation, it is suggested that
it be overridden if possible for performance.
.. index::
single: universal newlines; importlib.abc.InspectLoader.get_source method
.. versionchanged:: 3.4
No longer abstract and a concrete implementation is provided.
.. abstractmethod:: get_source(fullname)
An abstract method to return the source of a module. It is returned as
a text string using :term:`universal newlines`, translating all
recognized line separators into ``'\n'`` characters. Returns ``None``
if no source is available (e.g. a built-in module). Raises
:exc:`ImportError` if the loader cannot find the module specified.
.. versionchanged:: 3.4
Raises :exc:`ImportError` instead of :exc:`NotImplementedError`.
.. method:: is_package(fullname)
An optional method to return a true value if the module is a package, a
false value otherwise. :exc:`ImportError` is raised if the
:term:`loader` cannot find the module.
.. versionchanged:: 3.4
Raises :exc:`ImportError` instead of :exc:`NotImplementedError`.
.. staticmethod:: source_to_code(data, path='<string>')
Create a code object from Python source.
The *data* argument can be whatever the :func:`compile` function
supports (i.e. string or bytes). The *path* argument should be
the "path" to where the source code originated from, which can be an
abstract concept (e.g. location in a zip file).
With the subsequent code object one can execute it in a module by
running ``exec(code, module.__dict__)``.
.. versionadded:: 3.4
.. versionchanged:: 3.5
Made the method static.
.. method:: exec_module(module)
Implementation of :meth:`Loader.exec_module`.
.. versionadded:: 3.4
.. method:: load_module(fullname)
Implementation of :meth:`Loader.load_module`.
.. deprecated:: 3.4
use :meth:`exec_module` instead.
.. class:: ExecutionLoader
An abstract base class which inherits from :class:`InspectLoader` that,
when implemented, helps a module to be executed as a script. The ABC
represents an optional :pep:`302` protocol.
.. abstractmethod:: get_filename(fullname)
An abstract method that is to return the value of :attr:`__file__` for
the specified module. If no path is available, :exc:`ImportError` is
raised.
If source code is available, then the method should return the path to
the source file, regardless of whether a bytecode was used to load the
module.
.. versionchanged:: 3.4
Raises :exc:`ImportError` instead of :exc:`NotImplementedError`.
.. class:: FileLoader(fullname, path)
An abstract base class which inherits from :class:`ResourceLoader` and
:class:`ExecutionLoader`, providing concrete implementations of
:meth:`ResourceLoader.get_data` and :meth:`ExecutionLoader.get_filename`.
The *fullname* argument is a fully resolved name of the module the loader is
to handle. The *path* argument is the path to the file for the module.
.. versionadded:: 3.3
.. attribute:: name
The name of the module the loader can handle.
.. attribute:: path
Path to the file of the module.
.. method:: load_module(fullname)
Calls super's ``load_module()``.
.. deprecated:: 3.4
Use :meth:`Loader.exec_module` instead.
.. abstractmethod:: get_filename(fullname)
Returns :attr:`path`.
.. abstractmethod:: get_data(path)
Reads *path* as a binary file and returns the bytes from it.
.. class:: SourceLoader
An abstract base class for implementing source (and optionally bytecode)
file loading. The class inherits from both :class:`ResourceLoader` and
:class:`ExecutionLoader`, requiring the implementation of:
* :meth:`ResourceLoader.get_data`
* :meth:`ExecutionLoader.get_filename`
Should only return the path to the source file; sourceless
loading is not supported.
The abstract methods defined by this class are to add optional bytecode
file support. Not implementing these optional methods (or causing them to
raise :exc:`NotImplementedError`) causes the loader to
only work with source code. Implementing the methods allows the loader to
work with source *and* bytecode files; it does not allow for *sourceless*
loading where only bytecode is provided. Bytecode files are an
optimization to speed up loading by removing the parsing step of Python's
compiler, and so no bytecode-specific API is exposed.
.. method:: path_stats(path)
Optional abstract method which returns a :class:`dict` containing
metadata about the specified path. Supported dictionary keys are:
- ``'mtime'`` (mandatory): an integer or floating-point number
representing the modification time of the source code;
- ``'size'`` (optional): the size in bytes of the source code.
Any other keys in the dictionary are ignored, to allow for future
extensions. If the path cannot be handled, :exc:`OSError` is raised.
.. versionadded:: 3.3
.. versionchanged:: 3.4
Raise :exc:`OSError` instead of :exc:`NotImplementedError`.
.. method:: path_mtime(path)
Optional abstract method which returns the modification time for the
specified path.
.. deprecated:: 3.3
This method is deprecated in favour of :meth:`path_stats`. You don't
have to implement it, but it is still available for compatibility
purposes. Raise :exc:`OSError` if the path cannot be handled.
.. versionchanged:: 3.4
Raise :exc:`OSError` instead of :exc:`NotImplementedError`.
.. method:: set_data(path, data)
Optional abstract method which writes the specified bytes to a file
path. Any intermediate directories which do not exist are to be created
automatically.
When writing to the path fails because the path is read-only
(:attr:`errno.EACCES`/:exc:`PermissionError`), do not propagate the
exception.
.. versionchanged:: 3.4
No longer raises :exc:`NotImplementedError` when called.
.. method:: get_code(fullname)
Concrete implementation of :meth:`InspectLoader.get_code`.
.. method:: exec_module(module)
Concrete implementation of :meth:`Loader.exec_module`.
.. versionadded:: 3.4
.. method:: load_module(fullname)
Concrete implementation of :meth:`Loader.load_module`.
.. deprecated:: 3.4
Use :meth:`exec_module` instead.
.. method:: get_source(fullname)
Concrete implementation of :meth:`InspectLoader.get_source`.
.. method:: is_package(fullname)
Concrete implementation of :meth:`InspectLoader.is_package`. A module
is determined to be a package if its file path (as provided by
:meth:`ExecutionLoader.get_filename`) is a file named
``__init__`` when the file extension is removed **and** the module name
itself does not end in ``__init__``.
.. class:: Traversable
An object with a subset of pathlib.Path methods suitable for
@ -369,8 +136,8 @@
An abstract base class for resource readers capable of serving
the :meth:`importlib.resources.files` interface. Subclasses
:class:`importlib.abc.ResourceReader` and provides
concrete implementations of the :class:`importlib.abc.ResourceReader`'s
:class:`importlib.resources.abc.ResourceReader` and provides
concrete implementations of the :class:`importlib.resources.abc.ResourceReader`'s
abstract methods. Therefore, any loader supplying
:class:`importlib.abc.TraversableReader` also supplies ResourceReader.
@ -381,5 +148,5 @@
.. abstractmethod:: files()
Returns a :class:`importlib.abc.Traversable` object for the loaded
Returns a :class:`importlib.resources.abc.Traversable` object for the loaded
package.

View file

@ -17,7 +17,9 @@ text mode.
Resources are roughly akin to files inside directories, though it's important
to keep in mind that this is just a metaphor. Resources and packages **do
not** have to exist as physical files and directories on the file system.
not** have to exist as physical files and directories on the file system:
for example, a package and its resources can be imported from a zip file using
:py:mod:`zipimport`.
.. note::
@ -33,47 +35,36 @@ not** have to exist as physical files and directories on the file system.
on `using importlib.resources
<http://importlib-resources.readthedocs.io/en/latest/using.html>`_ and
`migrating from pkg_resources to importlib.resources
<http://importlib-resources.readthedocs.io/en/latest/migration.html>`_
and
`migrating legacy usage <https://importlib-resources.readthedocs.io/en/latest/using.html#migrating-from-legacy>`_.
<http://importlib-resources.readthedocs.io/en/latest/migration.html>`_.
Loaders that wish to support resource reading should implement a
:class:`Loaders <importlib.abc.Loader>` that wish to support resource reading should implement a
``get_resource_reader(fullname)`` method as specified by
:class:`importlib.abc.ResourceReader`.
The following types are defined.
:class:`importlib.resources.abc.ResourceReader`.
.. data:: Package
The ``Package`` type is defined as ``Union[str, ModuleType]``. This means
that where the function describes accepting a ``Package``, you can pass in
either a string or a module. Module objects must have a resolvable
``__spec__.submodule_search_locations`` that is not ``None``.
.. data:: Resource
This type describes the resource names passed into the various functions
in this package. This is defined as ``Union[str, os.PathLike]``.
The following functions are available.
Whenever a function accepts a ``Package`` argument, you can pass in
either a :class:`module object <types.ModuleType>` or a module name
as a string. You can only pass module objects whose
``__spec__.submodule_search_locations`` is not ``None``.
The ``Package`` type is defined as ``Union[str, ModuleType]``.
.. function:: files(package)
Returns an :class:`importlib.resources.abc.Traversable` object
Returns a :class:`~importlib.resources.abc.Traversable` object
representing the resource container for the package (think directory)
and its resources (think files). A Traversable may contain other
containers (think subdirectories).
*package* is either a name or a module object which conforms to the
``Package`` requirements.
:data:`Package` requirements.
.. versionadded:: 3.9
.. function:: as_file(traversable)
Given a :class:`importlib.resources.abc.Traversable` object representing
Given a :class:`~importlib.resources.abc.Traversable` object representing
a file, typically from :func:`importlib.resources.files`, return
a context manager for use in a :keyword:`with` statement.
The context manager provides a :class:`pathlib.Path` object.
@ -87,6 +78,22 @@ The following functions are available.
.. versionadded:: 3.9
Deprecated functions
--------------------
An older, deprecated set of functions is still available, but is
scheduled for removal in a future version of Python.
The main drawback of these functions is that they do not support
directories: they assume all resources are located directly within a *package*.
.. data:: Resource
For *resource* arguments of the functions below, you can pass in
the name of a resource as a string or
a :class:`path-like object <os.PathLike>`.
The ``Resource`` type is defined as ``Union[str, os.PathLike]``.
.. function:: open_binary(package, resource)
Open for binary reading the *resource* within *package*.
@ -97,7 +104,11 @@ The following functions are available.
sub-resources (i.e. it cannot be a directory). This function returns a
``typing.BinaryIO`` instance, a binary I/O stream open for reading.
.. deprecated:: 3.11
.. deprecated:: 3.11
Calls to this function can be replaced by::
files(package).joinpath(resource).open('rb')
.. function:: open_text(package, resource, encoding='utf-8', errors='strict')
@ -114,7 +125,11 @@ The following functions are available.
This function returns a ``typing.TextIO`` instance, a text I/O stream open
for reading.
.. deprecated:: 3.11
.. deprecated:: 3.11
Calls to this function can be replaced by::
files(package).joinpath(resource).open('r', encoding=encoding)
.. function:: read_binary(package, resource)
@ -128,7 +143,11 @@ The following functions are available.
sub-resources (i.e. it cannot be a directory). This function returns the
contents of the resource as :class:`bytes`.
.. deprecated:: 3.11
.. deprecated:: 3.11
Calls to this function can be replaced by::
files(package).joinpath(resource).read_bytes()
.. function:: read_text(package, resource, encoding='utf-8', errors='strict')
@ -143,7 +162,11 @@ The following functions are available.
have the same meaning as with built-in :func:`open`. This function
returns the contents of the resource as :class:`str`.
.. deprecated:: 3.11
.. deprecated:: 3.11
Calls to this function can be replaced by::
files(package).joinpath(resource).read_text(encoding=encoding)
.. function:: path(package, resource)
@ -160,17 +183,26 @@ The following functions are available.
within *package*; it may not contain path separators and it may not have
sub-resources (i.e. it cannot be a directory).
.. deprecated:: 3.11
.. deprecated:: 3.11
Calls to this function can be replaced using :func:`as_file`::
as_file(files(package).joinpath(resource))
.. function:: is_resource(package, name)
Return ``True`` if there is a resource named *name* in the package,
otherwise ``False``. Remember that directories are *not* resources!
otherwise ``False``.
This function does not consider directories to be resources.
*package* is either a name or a module object which conforms to the
``Package`` requirements.
.. deprecated:: 3.11
.. deprecated:: 3.11
Calls to this function can be replaced by::
files(package).joinpath(resource).is_file()
.. function:: contents(package)
@ -182,4 +214,8 @@ The following functions are available.
*package* is either a name or a module object which conforms to the
``Package`` requirements.
.. deprecated:: 3.11
.. deprecated:: 3.11
Calls to this function can be replaced by::
(resource.name for resource in files(package).iterdir() if resource.is_file())

View file

@ -401,7 +401,7 @@ ABC hierarchy::
Loaders that wish to support resource reading should implement a
:meth:`get_resource_reader` method as specified by
:class:`importlib.abc.ResourceReader`.
:class:`importlib.resources.abc.ResourceReader`.
.. versionchanged:: 3.7
Introduced the optional :meth:`get_resource_reader` method.
@ -508,7 +508,250 @@ ABC hierarchy::
The import machinery now takes care of this automatically.
.. include:: importlib.resources.abc.rst
.. class:: ResourceLoader
An abstract base class for a :term:`loader` which implements the optional
:pep:`302` protocol for loading arbitrary resources from the storage
back-end.
.. deprecated:: 3.7
This ABC is deprecated in favour of supporting resource loading
through :class:`importlib.resources.abc.ResourceReader`.
.. abstractmethod:: get_data(path)
An abstract method to return the bytes for the data located at *path*.
Loaders that have a file-like storage back-end
that allows storing arbitrary data
can implement this abstract method to give direct access
to the data stored. :exc:`OSError` is to be raised if the *path* cannot
be found. The *path* is expected to be constructed using a module's
:attr:`__file__` attribute or an item from a package's :attr:`__path__`.
.. versionchanged:: 3.4
Raises :exc:`OSError` instead of :exc:`NotImplementedError`.
.. class:: InspectLoader
An abstract base class for a :term:`loader` which implements the optional
:pep:`302` protocol for loaders that inspect modules.
.. method:: get_code(fullname)
Return the code object for a module, or ``None`` if the module does not
have a code object (as would be the case, for example, for a built-in
module). Raise an :exc:`ImportError` if loader cannot find the
requested module.
.. note::
While the method has a default implementation, it is suggested that
it be overridden if possible for performance.
.. index::
single: universal newlines; importlib.abc.InspectLoader.get_source method
.. versionchanged:: 3.4
No longer abstract and a concrete implementation is provided.
.. abstractmethod:: get_source(fullname)
An abstract method to return the source of a module. It is returned as
a text string using :term:`universal newlines`, translating all
recognized line separators into ``'\n'`` characters. Returns ``None``
if no source is available (e.g. a built-in module). Raises
:exc:`ImportError` if the loader cannot find the module specified.
.. versionchanged:: 3.4
Raises :exc:`ImportError` instead of :exc:`NotImplementedError`.
.. method:: is_package(fullname)
An optional method to return a true value if the module is a package, a
false value otherwise. :exc:`ImportError` is raised if the
:term:`loader` cannot find the module.
.. versionchanged:: 3.4
Raises :exc:`ImportError` instead of :exc:`NotImplementedError`.
.. staticmethod:: source_to_code(data, path='<string>')
Create a code object from Python source.
The *data* argument can be whatever the :func:`compile` function
supports (i.e. string or bytes). The *path* argument should be
the "path" to where the source code originated from, which can be an
abstract concept (e.g. location in a zip file).
With the subsequent code object one can execute it in a module by
running ``exec(code, module.__dict__)``.
.. versionadded:: 3.4
.. versionchanged:: 3.5
Made the method static.
.. method:: exec_module(module)
Implementation of :meth:`Loader.exec_module`.
.. versionadded:: 3.4
.. method:: load_module(fullname)
Implementation of :meth:`Loader.load_module`.
.. deprecated:: 3.4
use :meth:`exec_module` instead.
.. class:: ExecutionLoader
An abstract base class which inherits from :class:`InspectLoader` that,
when implemented, helps a module to be executed as a script. The ABC
represents an optional :pep:`302` protocol.
.. abstractmethod:: get_filename(fullname)
An abstract method that is to return the value of :attr:`__file__` for
the specified module. If no path is available, :exc:`ImportError` is
raised.
If source code is available, then the method should return the path to
the source file, regardless of whether a bytecode was used to load the
module.
.. versionchanged:: 3.4
Raises :exc:`ImportError` instead of :exc:`NotImplementedError`.
.. class:: FileLoader(fullname, path)
An abstract base class which inherits from :class:`ResourceLoader` and
:class:`ExecutionLoader`, providing concrete implementations of
:meth:`ResourceLoader.get_data` and :meth:`ExecutionLoader.get_filename`.
The *fullname* argument is a fully resolved name of the module the loader is
to handle. The *path* argument is the path to the file for the module.
.. versionadded:: 3.3
.. attribute:: name
The name of the module the loader can handle.
.. attribute:: path
Path to the file of the module.
.. method:: load_module(fullname)
Calls super's ``load_module()``.
.. deprecated:: 3.4
Use :meth:`Loader.exec_module` instead.
.. abstractmethod:: get_filename(fullname)
Returns :attr:`path`.
.. abstractmethod:: get_data(path)
Reads *path* as a binary file and returns the bytes from it.
.. class:: SourceLoader
An abstract base class for implementing source (and optionally bytecode)
file loading. The class inherits from both :class:`ResourceLoader` and
:class:`ExecutionLoader`, requiring the implementation of:
* :meth:`ResourceLoader.get_data`
* :meth:`ExecutionLoader.get_filename`
Should only return the path to the source file; sourceless
loading is not supported.
The abstract methods defined by this class are to add optional bytecode
file support. Not implementing these optional methods (or causing them to
raise :exc:`NotImplementedError`) causes the loader to
only work with source code. Implementing the methods allows the loader to
work with source *and* bytecode files; it does not allow for *sourceless*
loading where only bytecode is provided. Bytecode files are an
optimization to speed up loading by removing the parsing step of Python's
compiler, and so no bytecode-specific API is exposed.
.. method:: path_stats(path)
Optional abstract method which returns a :class:`dict` containing
metadata about the specified path. Supported dictionary keys are:
- ``'mtime'`` (mandatory): an integer or floating-point number
representing the modification time of the source code;
- ``'size'`` (optional): the size in bytes of the source code.
Any other keys in the dictionary are ignored, to allow for future
extensions. If the path cannot be handled, :exc:`OSError` is raised.
.. versionadded:: 3.3
.. versionchanged:: 3.4
Raise :exc:`OSError` instead of :exc:`NotImplementedError`.
.. method:: path_mtime(path)
Optional abstract method which returns the modification time for the
specified path.
.. deprecated:: 3.3
This method is deprecated in favour of :meth:`path_stats`. You don't
have to implement it, but it is still available for compatibility
purposes. Raise :exc:`OSError` if the path cannot be handled.
.. versionchanged:: 3.4
Raise :exc:`OSError` instead of :exc:`NotImplementedError`.
.. method:: set_data(path, data)
Optional abstract method which writes the specified bytes to a file
path. Any intermediate directories which do not exist are to be created
automatically.
When writing to the path fails because the path is read-only
(:attr:`errno.EACCES`/:exc:`PermissionError`), do not propagate the
exception.
.. versionchanged:: 3.4
No longer raises :exc:`NotImplementedError` when called.
.. method:: get_code(fullname)
Concrete implementation of :meth:`InspectLoader.get_code`.
.. method:: exec_module(module)
Concrete implementation of :meth:`Loader.exec_module`.
.. versionadded:: 3.4
.. method:: load_module(fullname)
Concrete implementation of :meth:`Loader.load_module`.
.. deprecated:: 3.4
Use :meth:`exec_module` instead.
.. method:: get_source(fullname)
Concrete implementation of :meth:`InspectLoader.get_source`.
.. method:: is_package(fullname)
Concrete implementation of :meth:`InspectLoader.is_package`. A module
is determined to be a package if its file path (as provided by
:meth:`ExecutionLoader.get_filename`) is a file named
``__init__`` when the file extension is removed **and** the module name
itself does not end in ``__init__``.
:mod:`importlib.machinery` -- Importers and path hooks

View file

@ -18,5 +18,6 @@ The full list of modules described in this chapter is:
runpy.rst
importlib.rst
importlib.resources.rst
importlib.resources.abc.rst
importlib.metadata.rst
sys_path_init.rst