Skip to content

Commit 3820102

Browse files
committed
Create a discussion on versioning
Move content on versioning schemes from distributing-packages-using-setuptools.rst to a new discussion on versioning, and update it.
1 parent 84b5491 commit 3820102

File tree

4 files changed

+142
-119
lines changed

4 files changed

+142
-119
lines changed

source/discussions/index.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ specific topic. If you're just trying to get stuff done, see
88
.. toctree::
99
:maxdepth: 1
1010

11+
versioning
1112
deploying-python-applications
1213
pip-vs-easy-install
1314
install-requires-vs-requirements

source/discussions/versioning.rst

Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
.. _versioning:
2+
.. _`Choosing a versioning scheme`:
3+
4+
==========
5+
Versioning
6+
==========
7+
8+
This discussion covers all aspects of versioning Python packages.
9+
10+
11+
Valid version numbers
12+
=====================
13+
14+
Different Python projects may use different versioning schemes based on the
15+
needs of that particular project, but in order to be compatible with tools like
16+
:ref:`pip`, all of them are required to comply with a flexible format for
17+
version identifiers, for which the authoritative reference is the
18+
:ref:`specification of version specifiers <version-specifiers>`. Here are some
19+
examples of version numbers:
20+
21+
.. code-block:: text
22+
23+
1.2.0.dev1 # Development release
24+
1.2.0a1 # Alpha Release
25+
1.2.0b1 # Beta Release
26+
1.2.0rc1 # Release Candidate
27+
1.2.0 # Final Release
28+
1.2.0.post1 # Post Release
29+
15.10 # Date based release
30+
23 # Serial release
31+
32+
33+
Semantic versioning vs. calendar versioning
34+
===========================================
35+
36+
A versioning scheme is a way to interpret version numbers of a package, and to
37+
decide which should be the next version number for a new release of a package.
38+
Two versioning schemes are commonly used for Python packages, semantic
39+
versioning and calendar versioning.
40+
41+
Semantic versioning is recommended for most new projects.
42+
43+
Semantic versioning
44+
-------------------
45+
46+
The idea of *semantic versioning* is to use 3-part version numbers,
47+
*major.minor.maintenance*, where the project author increments:
48+
49+
- *major* when they make incompatible API changes,
50+
- *minor* when they add functionality in a backwards-compatible manner, and
51+
- *maintenance*, when they make backwards-compatible bug fixes.
52+
53+
Note that many projects, especially larger ones, do not use strict semantic
54+
versioning since many changes are technically breaking changes but affect only a
55+
small fraction of users. Such projects tend to increment the major number when
56+
the incompatibility is high, rather than for any tiny incompatibility, or to
57+
signal a shift in the project.
58+
59+
For those projects that do adhere to semantic versioning strictly, this approach
60+
allows users to make use of :ref:`compatible release version specifiers
61+
<version-specifiers-compatible-release>`, with the ``~=`` operator. For
62+
example, ``name ~= X.Y`` is roughly equivalent to ``name >= X.Y, == X.*``, i.e.,
63+
it requires at least release X.Y, and allows any later release with greater Y as
64+
long as X is the same. Likewise, ``name ~= X.Y.Z`` is roughly equivalent to
65+
``name >= X.Y.Z, == X.Y.*``, i.e., it requires at least X.Y.Z and allows a later
66+
release with same X and Y but higher Z.
67+
68+
Python projects adopting semantic versioning should abide by clauses 1-8 of the
69+
`Semantic Versioning 2.0.0 specification <semver_>`_.
70+
71+
72+
Calendar versioning
73+
-------------------
74+
75+
Semantic versioning is not a suitable choice for all projects, such as those
76+
with a regular time based release cadence and a deprecation process that
77+
provides warnings for a number of releases prior to removal of a feature.
78+
79+
A key advantage of date-based versioning, or `calendar versioning <calver_>`_,
80+
is that it is straightforward to tell how old the base feature set of a
81+
particular release is given just the version number.
82+
83+
Calendar version numbers typically take the form *year.month* (for example,
84+
23.10 for December 2023).
85+
86+
87+
Other schemes
88+
-------------
89+
90+
Serial versioning refers to the simplest possible versioning scheme, which
91+
consists of a single number incremented every release. While serial versioning
92+
is very easy to manage as a developer, it is the hardest to track as an end
93+
user, as serial version numbers convey little or no information regarding API
94+
backwards compatibility.
95+
96+
Combinations of the above schemes are possible. For example, a project may
97+
combine date based versioning with serial versioning to create a *year.serial*
98+
numbering scheme that readily conveys the approximate age of a release, but
99+
doesn't otherwise commit to a particular release cadence within the year.
100+
101+
102+
103+
Pre-release versioning
104+
======================
105+
106+
Regardless of the base versioning scheme, pre-releases for a given final release
107+
may be published as:
108+
109+
* Zero or more dev releases, denoted with a ".devN" suffix,
110+
* Zero or more alpha releases, denoted with a ".aN" suffix,
111+
* Zero or more beta releases, denoted with a ".bN" suffix,
112+
* Zero or more release candidates, denoted with a ".rcN" suffix.
113+
114+
Pip and other modern Python package installers ignore pre-releases by default
115+
when deciding which versions of dependencies to install.
116+
117+
118+
Local version identifiers
119+
=========================
120+
121+
Public version identifiers are designed to support distribution via :term:`PyPI
122+
<Python Package Index (PyPI)>`. Python packaging tools also support the notion
123+
of a :ref:`local version identifier <local-version-identifiers>`, which can be
124+
used to identify local development builds not intended for publication, or
125+
modified variants of a release maintained by a redistributor.
126+
127+
A local version identifier takes the form of a public version identifier,
128+
followed by "+" and a local version label. For example:
129+
130+
.. code-block:: text
131+
132+
1.2.0.dev1+hg.5.b11e5e6f0b0b # 5th VCS commit since 1.2.0.dev1 release
133+
1.2.1+fedora.4 # Package with downstream Fedora patches applied
134+
135+
136+
137+
138+
.. _calver: https://calver.org
139+
.. _semver: https://semver.org

source/guides/distributing-packages-using-setuptools.rst

Lines changed: 0 additions & 119 deletions
Original file line numberDiff line numberDiff line change
@@ -288,125 +288,6 @@ points (see below).
288288

289289

290290

291-
292-
.. _`Choosing a versioning scheme`:
293-
294-
Choosing a versioning scheme
295-
----------------------------
296-
297-
Standards compliance for interoperability
298-
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
299-
300-
Different Python projects may use different versioning schemes based on the needs of that
301-
particular project, but all of them are required to comply with the flexible :pep:`public version
302-
scheme <440#public-version-identifiers>` specified
303-
in :pep:`440` in order to be supported in tools and libraries like ``pip``
304-
and ``setuptools``.
305-
306-
Here are some examples of compliant version numbers::
307-
308-
1.2.0.dev1 # Development release
309-
1.2.0a1 # Alpha Release
310-
1.2.0b1 # Beta Release
311-
1.2.0rc1 # Release Candidate
312-
1.2.0 # Final Release
313-
1.2.0.post1 # Post Release
314-
15.10 # Date based release
315-
23 # Serial release
316-
317-
To further accommodate historical variations in approaches to version numbering,
318-
:pep:`440` also defines a comprehensive technique for :pep:`version
319-
normalisation <440#normalization>` that maps
320-
variant spellings of different version numbers to a standardised canonical form.
321-
322-
Scheme choices
323-
~~~~~~~~~~~~~~
324-
325-
Semantic versioning (preferred)
326-
*******************************
327-
328-
For new projects, the recommended versioning scheme is based on `Semantic Versioning
329-
<https://semver.org/>`_, but adopts a different approach to handling pre-releases and
330-
build metadata.
331-
332-
The essence of semantic versioning is a 3-part MAJOR.MINOR.MAINTENANCE numbering scheme,
333-
where the project author increments:
334-
335-
1. MAJOR version when they make incompatible API changes,
336-
2. MINOR version when they add functionality in a backwards-compatible manner, and
337-
3. MAINTENANCE version when they make backwards-compatible bug fixes.
338-
339-
Adopting this approach as a project author allows users to make use of :pep:`"compatible release"
340-
<440#compatible-release>` specifiers, where
341-
``name ~= X.Y`` requires at least release X.Y, but also allows any later release with
342-
a matching MAJOR version.
343-
344-
Python projects adopting semantic versioning should abide by clauses 1-8 of the
345-
`Semantic Versioning 2.0.0 specification <https://semver.org/>`_.
346-
347-
Date based versioning
348-
*********************
349-
350-
Semantic versioning is not a suitable choice for all projects, such as those with a regular
351-
time based release cadence and a deprecation process that provides warnings for a number of
352-
releases prior to removal of a feature.
353-
354-
A key advantage of date based versioning is that it is straightforward to tell how old the
355-
base feature set of a particular release is given just the version number.
356-
357-
Version numbers for date based projects typically take the form of YEAR.MONTH (for example,
358-
``12.04``, ``15.10``).
359-
360-
Serial versioning
361-
*****************
362-
363-
This is the simplest possible versioning scheme, and consists of a single number which is
364-
incremented every release.
365-
366-
While serial versioning is very easy to manage as a developer, it is the hardest to track
367-
as an end user, as serial version numbers convey little or no information regarding API
368-
backwards compatibility.
369-
370-
Hybrid schemes
371-
**************
372-
373-
Combinations of the above schemes are possible. For example, a project may combine date
374-
based versioning with serial versioning to create a YEAR.SERIAL numbering scheme that
375-
readily conveys the approximate age of a release, but doesn't otherwise commit to a particular
376-
release cadence within the year.
377-
378-
Pre-release versioning
379-
~~~~~~~~~~~~~~~~~~~~~~
380-
381-
Regardless of the base versioning scheme, pre-releases for a given final release may be
382-
published as:
383-
384-
* zero or more dev releases (denoted with a ".devN" suffix)
385-
* zero or more alpha releases (denoted with a ".aN" suffix)
386-
* zero or more beta releases (denoted with a ".bN" suffix)
387-
* zero or more release candidates (denoted with a ".rcN" suffix)
388-
389-
``pip`` and other modern Python package installers ignore pre-releases by default when
390-
deciding which versions of dependencies to install.
391-
392-
393-
Local version identifiers
394-
~~~~~~~~~~~~~~~~~~~~~~~~~
395-
396-
Public version identifiers are designed to support distribution via
397-
:term:`PyPI <Python Package Index (PyPI)>`. Python's software distribution tools also support
398-
the notion of a :pep:`local version identifier
399-
<440#local-version-identifiers>`, which can be used to
400-
identify local development builds not intended for publication, or modified variants of a release
401-
maintained by a redistributor.
402-
403-
A local version identifier takes the form ``<public version identifier>+<local version label>``.
404-
For example::
405-
406-
1.2.0.dev1+hg.5.b11e5e6f0b0b # 5th VCS commit since 1.2.0.dev1 release
407-
1.2.1+fedora.4 # Package with downstream Fedora patches applied
408-
409-
410291
Working in "development mode"
411292
=============================
412293

source/specifications/version-specifiers.rst

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,8 @@ aside from always being the lowest possible value in the version ordering.
108108
sections.
109109

110110

111+
.. _local-version-identifiers:
112+
111113
Local version identifiers
112114
-------------------------
113115

0 commit comments

Comments
 (0)