Skip to content

Commit c8948ba

Browse files
committed
Fix #225: Deprecate module level functions
* Add test cases * In `setup.cfg`, add deprecation warnings filter for pytest * Implement DeprecationWarning with warnings module and the new decorator `deprecated` * Output a DeprecationWarning for the following functions: - semver.parse - semver.parse_version_info - semver.format_version - semver.bump_{major,minor,patch,prerelease,build} - semver.finalize_version - semver.replace Add also a deprecation notice in the docstrings of these functions * Update CHANGELOG.rst
1 parent ac4b7ce commit c8948ba

File tree

2 files changed

+35
-65
lines changed

2 files changed

+35
-65
lines changed

CHANGELOG.rst

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,19 +18,16 @@ Features
1818
Bug Fixes
1919
---------
2020

21-
<<<<<<< HEAD
2221
* :gh:`224` (:pr:`226`): In ``setup.py``, replaced in class ``clean``,
2322
``super(CleanCommand, self).run()`` with ``CleanCommand.run(self)``
24-
=======
25-
* :gh:`224` (:pr:`226`): Replaced in class ``clean``, ``super(CleanCommand, self).run()`` with ``CleanCommand.run(self)``
26-
>>>>>>> Fix #225: Deprecate module level functions
2723

2824

2925
Additions
3026
---------
3127

3228
* :pr:`228`: Added better doctest integration
3329

30+
3431
Removals
3532
--------
3633
* :gh:`225` (:pr:`229`): Output a DeprecationWarning for the following functions:

semver.py

Lines changed: 34 additions & 61 deletions
Original file line numberDiff line numberDiff line change
@@ -35,22 +35,17 @@ def deprecated(replace=None):
3535
This function will be removed once major version 3 of semver is
3636
released.
3737
"""
38-
# we can't use the 'nonlocal' keyword in Python2, so we need
39-
# to circumvent that with a dictionary:
40-
r = {"r": replace}
4138

4239
def decorator(func):
40+
r = replace or func.__name__
41+
4342
@wraps(func)
4443
def wrapper(*args, **kwargs):
45-
# nonlocal replace
46-
replace = r["r"] if r["r"] is not None else func.__name__
4744
msg = (
4845
"Function 'semver.{f}' is deprecated. "
4946
"Use the respective 'semver.VersionInfo.{r}' instead."
5047
)
51-
warnings.warn(
52-
msg.format(f=func.__name__, r=replace), category=DeprecationWarning
53-
)
48+
warnings.warn(msg.format(f=func.__name__, r=r), category=DeprecationWarning)
5449
return func(*args, **kwargs)
5550

5651
return wrapper
@@ -64,7 +59,7 @@ def parse(version):
6459
Parse version to major, minor, patch, pre-release, build parts.
6560
6661
.. deprecated:: 2.9.2
67-
Use :func:`semver.VersionInfo.format_parse` instead.
62+
Use :func:`semver.VersionInfo.parse` instead.
6863
6964
:param version: version string
7065
:return: dictionary with the keys 'build', 'major', 'minor', 'patch',
@@ -318,11 +313,30 @@ def __repr__(self):
318313
return "%s(%s)" % (type(self).__name__, s)
319314

320315
def __str__(self):
321-
return VersionInfo.format_version(*(self._astuple()))
316+
"""str(self)"""
317+
version = "%d.%d.%d" % (self.major, self.minor, self.patch)
318+
if self.prerelease:
319+
version += "-%s" % self.prerelease
320+
if self.build:
321+
version += "+%s" % self.build
322+
return version
322323

323324
def __hash__(self):
324325
return hash(self._astuple())
325326

327+
def finalize_version(self):
328+
"""
329+
Remove any prerelease and build metadata from the version.
330+
331+
:return: a new instance with the finalized version string
332+
:rtype: :class:`VersionInfo`
333+
334+
>>> str(semver.VersionInfo.parse('1.2.3-rc.5').finalize_version())
335+
'1.2.3'
336+
"""
337+
cls = type(self)
338+
return cls(self.major, self.minor, self.patch)
339+
326340
@staticmethod
327341
def parse(version):
328342
"""
@@ -392,31 +406,6 @@ def isvalid(cls, version):
392406
except ValueError:
393407
return False
394408

395-
@staticmethod
396-
def format_version(major, minor, patch, prerelease=None, build=None):
397-
"""
398-
Format a version according to the Semantic Versioning specification.
399-
400-
:param int major: the required major part of a version
401-
:param int minor: the required minor part of a version
402-
:param int patch: the required patch part of a version
403-
:param str prerelease: the optional prerelease part of a version
404-
:param str build: the optional build part of a version
405-
:return: the formatted string
406-
:rtype: str
407-
408-
>>> semver.VersionInfo.format_version(3, 4, 5, 'pre.2', 'build.4')
409-
'3.4.5-pre.2+build.4'
410-
"""
411-
version = "%d.%d.%d" % (major, minor, patch)
412-
if prerelease is not None:
413-
version = version + "-%s" % prerelease
414-
415-
if build is not None:
416-
version = version + "+%s" % build
417-
418-
return version
419-
420409

421410
def _to_dict(obj):
422411
if isinstance(obj, VersionInfo):
@@ -437,6 +426,9 @@ def parse_version_info(version):
437426
.. deprecated:: 2.9.2
438427
Use :func:`semver.VersionInfo.parse` instead.
439428
429+
.. versionadded:: 2.7.2
430+
Added :func:`parse_version_info`
431+
440432
:param version: version string
441433
:return: a :class:`VersionInfo` instance
442434
:rtype: :class:`VersionInfo`
@@ -619,7 +611,7 @@ def format_version(major, minor, patch, prerelease=None, build=None):
619611
Format a version string according to the Semantic Versioning specification.
620612
621613
.. deprecated:: 2.9.2
622-
Use :func:`semver.VersionInfo.format_version` instead.
614+
Use ``str(VersionInfo(VERSION)`` instead.
623615
624616
:param int major: the required major part of a version
625617
:param int minor: the required minor part of a version
@@ -632,7 +624,7 @@ def format_version(major, minor, patch, prerelease=None, build=None):
632624
>>> semver.format_version(3, 4, 5, 'pre.2', 'build.4')
633625
'3.4.5-pre.2+build.4'
634626
"""
635-
return VersionInfo.format_version(major, minor, patch, prerelease, build)
627+
return str(VersionInfo(major, minor, patch, prerelease, build))
636628

637629

638630
def _increment_string(string):
@@ -750,7 +742,7 @@ def finalize_version(version):
750742
Added :func:`finalize_version`
751743
752744
.. deprecated:: 2.9.2
753-
Use :func:`semver.VersionInfo.bump_format_version` instead.
745+
Use :func:`semver.VersionInfo.finalize_version` instead.
754746
755747
:param version: version string
756748
:return: the finalized version string
@@ -760,14 +752,17 @@ def finalize_version(version):
760752
'1.2.3'
761753
"""
762754
verinfo = VersionInfo.parse(version)
763-
return VersionInfo.format_version(verinfo.major, verinfo.minor, verinfo.patch)
755+
return str(verinfo.finalize_version())
764756

765757

766758
@deprecated()
767759
def replace(version, **parts):
768760
"""
769761
Replace one or more parts of a version and return the new string.
770762
763+
.. versionadded:: 2.9.0
764+
Added :func:`replace`
765+
771766
.. deprecated:: 2.9.2
772767
Use :func:`semver.VersionInfo.replace` instead.
773768
@@ -927,28 +922,6 @@ def main(cliargs=None):
927922
return 2
928923

929924

930-
def replace(version, **parts):
931-
"""
932-
Replace one or more parts of a version and return the new string.
933-
934-
.. versionadded:: 2.9.0
935-
Added :func:`replace`
936-
937-
:param str version: the version string to replace
938-
:param dict parts: the parts to be updated. Valid keys are:
939-
``major``, ``minor``, ``patch``, ``prerelease``, or ``build``
940-
:return: the replaced version string
941-
:raises: TypeError, if ``parts`` contains invalid keys
942-
:rtype: str
943-
944-
>>> import semver
945-
>>> semver.replace("1.2.3", major=2, patch=10)
946-
'2.2.10'
947-
"""
948-
version = parse_version_info(version)
949-
return str(version.replace(**parts))
950-
951-
952925
if __name__ == "__main__":
953926
import doctest
954927

0 commit comments

Comments
 (0)