PEP 426 updates

* Add implementation_name and implementation_version marker variables
* Expand on the expected use cases for supports_environments
* Reference wheel and warehouse from legacy metadata appendix
* Drop most of the Sphinx notes (moving some to Rejected Features)
This commit is contained in:
Nick Coghlan 2013-06-23 17:01:36 +10:00
parent 5e32d4908d
commit f8a1a5ce04
1 changed files with 112 additions and 97 deletions

View File

@ -13,7 +13,7 @@ Content-Type: text/x-rst
Requires: 440
Created: 30 Aug 2012
Post-History: 14 Nov 2012, 5 Feb 2013, 7 Feb 2013, 9 Feb 2013,
27 May 2013, 20 Jun 2013
27 May 2013, 20 Jun 2013, 23 Jun 2013
Replaces: 345
@ -225,6 +225,9 @@ along with the supporting metadata file formats defined by the
objects as strings consisting of a Python module name and a module
attribute name, separated by a colon. For example: ``"test.regrtest:main"``.
"Distros" is used as the preferred term for Linux distributions, to help
avoid confusion with the Python-specific meaning of the term.
Integration and deployment of distributions
-------------------------------------------
@ -545,28 +548,6 @@ Example::
"name": "ComfyChair"
.. note::
Debian doesn't actually permit underscores in names, but that seems
unduly restrictive for this spec given the common practice of using
valid Python identifiers as Python distribution names. A Debian side
policy of converting underscores to hyphens seems easy enough to
implement (and the requirement to consider hyphens and underscores as
equivalent ensures that doing so won't introduce any conflicts).
We're deliberately *not* following Python 3 down the path of arbitrary
unicode identifiers at this time. The security implications of doing so
are substantially worse in the software distribution use case (it opens
up far more interesting attack vectors than mere code obfuscation), the
existing tooling really only works properly if you abide by the stated
restrictions and changing it would require a *lot* of work for all
the automated tools in the chain.
PyPI has recently been updated to reject non-compliant names for newly
registered projects, and the ~230 existing non-compliant names have
been updated to become compliant (mostly by replacing spaces with
hyphens).
Version
-------
@ -665,33 +646,6 @@ Example::
"source_url": "http://github.com/pypa/pip/archive/1.3.1.zip#sha1=da9234ee9982d4bbb3c72346a6de940a148ea686"
"source_url": "git+https://github.com/pypa/pip.git@1.3.1"
.. note::
This was called "Download-URL" in previous versions of the metadata. It
has been renamed, since there are plenty of other download locations and
this URL is meant to be a way to get the original source for development
purposes (or to generate an SRPM or other platform specific equivalent).
For extra fun and games, it appears that unlike "svn+ssh://",
neither "git+ssh://" nor "hg+ssh://" natively support direct linking to a
particular tag (hg does support direct links to bookmarks through the URL
fragment, but that doesn't help for git and doesn't appear to be what I
want anyway).
However pip does have a `defined convention
<http://www.pip-installer.org/en/latest/logic.html#vcs-support>`__ for
this kind of link, which effectively splits a "URL" into "<repo>@<tag>".
The PEP simply adopts pip's existing solution to this problem.
This field is separate from the project URLs, as it's expected to
change for each version, while the project URLs are expected to
be fairly stable.
Note that many translations of legacy metadata won't be able to convert
Download-URL to source_url, as many distributions haven't respected the
requirement to link to a specific version.
Additional descriptive metadata
===============================
@ -851,15 +805,6 @@ The defined contributor roles are as follows:
* ``contributor``: any other individuals or organizations involved in the
creation of the distribution
.. note::
The contributor role field is included primarily to replace the
Author, Author-Email, Maintainer, Maintainer-Email fields from metadata
1.2 in a way that allows those distinctions to be fully represented for
lossless translation, while allowing future distributions to pretty
much ignore everything other than the contact/contributor distinction
if they so choose.
Contact and contributor metadata is optional. Automated tools MUST operate
correctly if a distribution does not provide it, including failing cleanly
when an operation depending on one of these fields is requested.
@ -971,18 +916,6 @@ Distributions may declare five differents kinds of dependency:
Dependency management is heavily dependent on the version identification
and specification scheme defined in PEP 440.
.. note::
This substantially changes the old two-phase setup vs runtime dependency
model in metadata 1.2 (which was in turn derived from the setuptools
dependency parameters). The translation is that ``dev_requires`` and
``build_requires`` both map to ``Setup-Requires-Dist``
in 1.2 (aka ``install_requires`` in setuptools), while ``run_requires``
and ``meta_requires`` map to ``Requires-Dist``.
To go the other way, ``Setup-Requires-Dist`` maps to ``build_requires``
and ``Requires-Dist`` maps to ``meta_requires`` (for exact comparisons)
and ``run_requires`` (for all other version specifiers).
All of these fields are optional. Automated tools MUST operate correctly if
a distribution does not provide them, by assuming that a missing field
indicates "Not applicable for this distribution".
@ -1043,13 +976,6 @@ Note that the same extras and environment markers MAY appear in multiple
conditional dependencies. This may happen, for example, if an extra itself
only needs some of its dependencies in specific environments.
.. note::
Technically, you could store the conditional and unconditional
dependencies in a single list and switch based on the entry type
(string or mapping), but the ``*requires`` vs ``*may-require`` two
list design seems easier to understand and work with.
Mapping dependencies to development and distribution activities
---------------------------------------------------------------
@ -1137,8 +1063,8 @@ uploaded distributions. Direct references are intended as a tool for
software integrators rather than publishers.
Distributions that rely on direct references to platform specific binary
archives SHOULD place appropriate entries in their ``supports_environments``
field.
archives SHOULD define appropriate constraints in their
``supports_environments`` field.
Example::
@ -1167,8 +1093,8 @@ uploaded distributions. Direct references are intended as a tool for
software integrators rather than publishers.
Distributions that rely on direct references to platform specific binary
archives SHOULD place appropriate entries in their ``supports_environments``
field.
archives SHOULD defined appropriate constraints in their
``supports_environments`` field.
Example::
@ -1468,26 +1394,43 @@ distribution supports any platform supported by Python.
Individual entries are environment markers, as described in
`Environment markers`_.
Installation tools SHOULD report an error if supported platforms are
Installation tools SHOULD report an error if supported environments are
specified by the distribution and the current platform fails to match
any of them, MUST at least emit a warning, and MAY allow the user to
force the installation to proceed regardless.
Examples::
The two main uses of this field are to declare which versions of Python
and which underlying operating systems are supported.
Examples indicating supported Python versions::
# Supports Python 2.6+
"supports_environments": ["python_version >= '2.6'"]
# Supports Python 2.6+ (for 2.x) or 3.3+ (for 3.x)
"supports_environments": ["python_version >= '3.3'",
"'3.0' > python_version >= '2.6'"]
Examples indicating supported operating systems::
# Windows only
"supports_environments": ["sys_platform == 'win32'"]
# Anything except Windows
"supports_environments": ["sys_platform != 'win32'"]
# Linux or BSD only
"supports_environments": ["'linux' in sys_platform",
"'bsd' in sys_platform"]
Example where the supported Python version varies by platform::
.. note::
This field replaces the old Platform, Requires-Platform and
Requires-Python fields and has been redesigned with environment
marker based semantics that should make it possible to reliably flag,
for example, Unix specific or Windows specific distributions, as well
as Python 2 only and Python 3 only distributions.
# The standard library's os module has long supported atomic renaming
# on POSIX systems, but only gained atomic renaming on Windows in Python
# 3.3. A distribution that needs atomic renaming support for reliable
# operation might declare the following supported environments.
"supports_environments": ["python_version >= '2.6' and sys_platform != 'win32'",
"python_version >= '3.3' and sys_platform == 'win32'"]
Install hooks
@ -1615,6 +1558,12 @@ To avoid name conflicts, it is RECOMMENDED that distribution names be used
to identify metadata extensions. This practice will also make it easier to
find authoritative documentation for metadata extensions.
Metadata extensions allow development tools to record information in the
metadata that may be useful during later phases of distribution. For
example, a build tool could include default build options in a metadata
extension when creating an sdist, and use those when creating the wheel
files later.
Extras (optional dependencies)
==============================
@ -1766,6 +1715,12 @@ where ``SUBEXPR`` is either a Python string (such as ``'2.4'``, or
* ``platform_version``: ``platform.version()``
* ``platform_machine``: ``platform.machine()``
* ``platform_python_implementation``: ``platform.python_implementation()``
* ``implementation_name````: ``sys.implementation.name``
* ``implementation_version````: see definition below
If a particular value is not available (such as the ``sys.implementation``
subattributes in versions of Python prior to 3.3), the corresponding marker
variable MUST be considered equivalent to the empty string.
Note that all subexpressions are restricted to strings or one of the
marker variable names (which refer to string values), meaning that it is
@ -1775,17 +1730,20 @@ side of the ``in`` and ``not in`` operators.
Chaining of comparison operations is permitted using the normal Python
semantics of an implied ``and``.
The ``python_full_version`` marker variable is derived from
``sys.version_info()`` in accordance with the following algorithm::
The ``python_full_version`` and ``implementation_version`` marker variables
are derived from ``sys.version_info()`` and ``sys.implementation.version``
respectively, in accordance with the following algorithm::
def format_full_version():
info = sys.version_info
def format_full_version(info):
version = '{0.major}.{0.minor}.{0.micro}'.format(info)
kind = info.releaselevel
if kind != 'final':
version += kind[0] + str(info.serial)
return version
python_full_version = format_full_version(sys.version_info)
implementation_version = format_full_version(sys.implementation.version)
``python_full_version`` will typically correspond to the leading segment
of ``sys.version()``.
@ -1804,14 +1762,29 @@ defined in a new PEP.
Appendix A: Conversion notes for legacy metadata
================================================
TBD pending feedback from Daniel & Donald
The reference implementations for converting from legacy metadata to
metadata 2.0 are Daniel Holth's `wheel project
<https://bitbucket.org/dholth/wheel/overview>`__ (which
adds the ``bdist_wheel`` command to ``setuptools``) and Donald Stufft's
`Warehouse project <https://github.com/dstufft/warehouse>`__ (which will
eventually be the next generation Python Package Index implementation).
While it is expected that there may be some edge cases where manual
intervention is needed for clean conversion, the specification has been
designed to allow fully automated conversion of almost all projects on
PyPI.
Metadata conversion (especially on the part of the index server) is a
necessary step to allow installation and analysis tools to start
benefiting from the new metadata format, without having to wait for
developers to upgrade to newer build systems.
Appendix B: Mapping dependency declarations to an RPM SPEC file
===============================================================
As an example of mapping this to Linux distro packages, assume an
As an example of mapping this PEP to Linux distro packages, assume an
example project without any extras defined is split into 2 RPMs
in a SPEC file: ``example`` and ``example-devel``.
@ -2362,6 +2335,48 @@ introducing too much additional complexity for too small a gain in
expressiveness.
Disallowing underscores in distribution names
---------------------------------------------
Debian doesn't actually permit underscores in names, but that seems
unduly restrictive for this spec given the common practice of using
valid Python identifiers as Python distribution names. A Debian side
policy of converting underscores to hyphens seems easy enough to
implement (and the requirement to consider hyphens and underscores as
equivalent ensures that doing so won't introduce any conflicts).
Allowing the use of Unicode in distribution names
-------------------------------------------------
This PEP deliberately avoids following Python 3 down the path of arbitrary
Unicode identifiers, as the security implications of doing so are
substantially worse in the software distribution use case (it opens
up far more interesting attack vectors than mere code obfuscation).
In addition, the existing tools really only work properly if you restrict
names to ASCII and changing that would require a *lot* of work for all
the automated tools in the chain.
It may be reasonable to revisit this question at some point in the (distant)
future, but setting up a more reliable software distribution system is
challenging enough without adding more general Unicode identifier support
into the mix.
Single list for conditional and unconditional dependencies
----------------------------------------------------------
It's technically possible to store the conditional and unconditional
dependencies of each kind in a single list and switch the handling based on
the entry type (string or mapping).
However, the current ``*requires`` vs ``*may-require`` two list design seems
easier to understand and work with, since it's only the conditional
dependencies that need to be checked against the requested extras list and
the target installation environment.
Depending on source labels
--------------------------