diff --git a/setup.cfg b/setup.cfg index 39193949..542bc314 100644 --- a/setup.cfg +++ b/setup.cfg @@ -29,6 +29,7 @@ install_requires = dictdiffer importlib-resources psutil + packaging [options.packages.find] where = src diff --git a/src/sinol_make/__init__.py b/src/sinol_make/__init__.py index f7aa5f70..fb6de466 100644 --- a/src/sinol_make/__init__.py +++ b/src/sinol_make/__init__.py @@ -79,6 +79,9 @@ def main_exn(): def main(): new_version = None try: + if util.is_dev(__version__): + print(util.warning('You are using a development version of sinol-make. ' + 'It may be unstable and contain bugs.')) new_version = util.check_for_updates(__version__) main_exn() except argparse.ArgumentError as err: @@ -92,6 +95,12 @@ def main(): 'https://github.com/sio2project/sinol-make/#reporting-bugs-and-contributing-code') finally: if new_version is not None: - print(util.warning( - f'New version of sinol-make is available (your version: {__version__}, available version: ' - f'{new_version}).\nYou can update it by running `pip3 install sinol-make --upgrade`.')) + if not util.is_dev(new_version): + print(util.warning( + f'New version of sinol-make is available (your version: {__version__}, available version: ' + f'{new_version}).\nYou can update it by running `pip3 install sinol-make --upgrade`.')) + elif util.is_dev(new_version): + print(util.warning( + f'New development version of sinol-make is available (your version: {__version__}, available ' + f'version: {new_version}).\nYou can update it by running `pip3 install sinol-make --pre --upgrade`.' + )) diff --git a/src/sinol_make/util.py b/src/sinol_make/util.py index eb7a7888..a5813db6 100644 --- a/src/sinol_make/util.py +++ b/src/sinol_make/util.py @@ -7,6 +7,7 @@ import multiprocessing import resource from typing import Union +from packaging.version import parse as parse_version from sinol_make.contest_types import get_contest_type from sinol_make.helpers import paths, cache @@ -150,10 +151,18 @@ def import_importlib_resources(): return importlib -def check_for_updates(current_version) -> Union[str, None]: +def is_dev(version): + """ + Function to check if the version is a development version. + """ + return parse_version(version).is_devrelease + + +def check_for_updates(current_version, check=True) -> Union[str, None]: """ Function to check if there is a new version of sinol-make. :param current_version: current version of sinol-make + :param check: whether to check for new version :return: returns new version if there is one, None otherwise """ importlib = import_importlib_resources() @@ -164,8 +173,9 @@ def check_for_updates(current_version) -> Union[str, None]: # We check for new version asynchronously, so that it doesn't slow down the program. # If the main process exits, the check_version process will also exit. - process = multiprocessing.Process(target=check_version, daemon=True) - process.start() + if check: + process = multiprocessing.Process(target=check_version, daemon=True) + process.start() version_file = data_dir.joinpath("version") try: @@ -178,7 +188,9 @@ def check_for_updates(current_version) -> Union[str, None]: return None try: - if compare_versions(current_version, version) == -1: + if not is_dev(version) and parse_version(version) > parse_version(current_version): + return version + if is_dev(current_version) and is_dev(version) and parse_version(version) > parse_version(current_version): return version else: return None @@ -217,26 +229,6 @@ def check_version(): pass -def compare_versions(version_a, version_b): - """ - Function to compare two versions. - Returns 1 if version_a > version_b, 0 if version_a == version_b, -1 if version_a < version_b. - """ - - def convert(version): - return tuple(map(int, version.split("."))) - - version_a = convert(version_a) - version_b = convert(version_b) - - if version_a > version_b: - return 1 - elif version_a == version_b: - return 0 - else: - return -1 - - def lines_diff(lines1, lines2): """ Function to compare two lists of lines. diff --git a/tests/test_util.py b/tests/test_util.py index e95f69bf..592020a4 100644 --- a/tests/test_util.py +++ b/tests/test_util.py @@ -44,28 +44,6 @@ def test_file_diff(): assert util.file_diff(a_file, b_file) is False -def test_compare_versions(): - """ - Tests for compare_versions function - """ - - assert util.compare_versions('1.0.0', '1.0.0') == 0 - assert util.compare_versions('1.0.0', '1.0.1') == -1 - assert util.compare_versions('1.0.1', '1.0.0') == 1 - assert util.compare_versions('1.0.0', '1.1.0') == -1 - assert util.compare_versions('1.1.0', '1.0.0') == 1 - assert util.compare_versions('1.0.0', '2.0.0') == -1 - assert util.compare_versions('2.0.0', '1.0.0') == 1 - with pytest.raises(ValueError): - util.compare_versions('1.0.0', '') - with pytest.raises(ValueError): - util.compare_versions('', '1.0.0') - with pytest.raises(ValueError): - util.compare_versions('1.0.0', 'abc') - with pytest.raises(ValueError): - util.compare_versions('abc', '1.0.0') - - @requests_mock.Mocker(kw="mocker") def test_check_version(**kwargs): """ @@ -74,6 +52,29 @@ def test_check_version(**kwargs): """ mocker = kwargs["mocker"] + mocker.get("https://pypi.python.org/pypi/sinol-make/json", json={"info": {"version": "1.0.0.dev2"}}) + util.check_version() + version = util.check_for_updates("1.0.0.dev1", False) + assert version == "1.0.0.dev2" + assert util.is_dev(version) + + mocker.get("https://pypi.python.org/pypi/sinol-make/json", json={"info": {"version": "1.0.0"}}) + util.check_version() + version = util.check_for_updates("1.0.0.dev1", False) + assert version == "1.0.0" + assert not util.is_dev(version) + + mocker.get("https://pypi.python.org/pypi/sinol-make/json", json={"info": {"version": "2.0.0.dev1"}}) + util.check_version() + version = util.check_for_updates("1.0.0", False) + assert version is None + + mocker.get("https://pypi.python.org/pypi/sinol-make/json", json={"info": {"version": "1.0.1"}}) + util.check_version() + version = util.check_for_updates("1.0.0", False) + assert version == "1.0.1" + assert not util.is_dev(version) + importlib = util.import_importlib_resources() data_dir = importlib.files('sinol_make').joinpath("data")