diff --git a/scripts/bump_pyproject_version.py b/scripts/bump_pyproject_version.py index e6a64b21..10502e0e 100644 --- a/scripts/bump_pyproject_version.py +++ b/scripts/bump_pyproject_version.py @@ -26,11 +26,14 @@ def read_pyproject_version(file_path): def bump_version(current_version, bump_type): """ Bumps the current version up using semantic versioning. - This function also supports bumping versions that have a dev segment. + This function supports: + - Bumping a stable version to start a dev cycle. + - Bumping within a dev cycle. + - Finalizing a dev version (i.e. removing the .dev suffix). Args: - current_version (str): The current version (e.g. "0.1.0" or "0.6.0.dev1"). - bump_type (str): Type of bump: "major", "minor", or "patch". + current_version (str): The current version (e.g. "1.0.0" or "1.0.1.dev2"). + bump_type (str): Type of bump: "major", "minor", "patch", or "finalize". Returns: str: The new version string. @@ -40,33 +43,39 @@ def bump_version(current_version, bump_type): except InvalidVersion as e: raise ValueError(f"Invalid current version '{current_version}': {e}") - # Determine if this is a dev release. + # Is this a dev version? is_dev = ver.dev is not None major, minor, patch = ver.release - if bump_type == "major": + if bump_type == "finalize": + if is_dev: + # Remove the dev segment to finalize this dev release. + new_version = f"{major}.{minor}.{patch}" + else: + raise ValueError("Current version is stable; nothing to finalize.") + elif bump_type == "major": major += 1 minor = 0 patch = 0 new_version = f"{major}.{minor}.{patch}" - if is_dev: - new_version += ".dev1" + # Always start a dev cycle for a bump if desired. + new_version += ".dev1" elif bump_type == "minor": minor += 1 patch = 0 new_version = f"{major}.{minor}.{patch}" - if is_dev: - new_version += ".dev1" + new_version += ".dev1" elif bump_type == "patch": if is_dev: - # Bump the dev counter (e.g. 0.6.0.dev1 -> 0.6.0.dev2). + # If already in a dev cycle, bump the dev counter. new_dev = ver.dev + 1 new_version = f"{major}.{minor}.{patch}.dev{new_dev}" else: + # For a stable version, bump the patch and start a dev cycle. patch += 1 - new_version = f"{major}.{minor}.{patch}" + new_version = f"{major}.{minor}.{patch}.dev1" else: - raise ValueError("bump_type must be one of: 'major', 'minor', 'patch'") + raise ValueError("bump_type must be one of: 'major', 'minor', 'patch', or 'finalize'") return new_version @@ -114,12 +123,12 @@ def update_pyproject_version(file_path, new_version): def main(): parser = argparse.ArgumentParser( - description="Bump or set version in pyproject.toml using semantic versioning. Supports .dev versions." + description="Bump or set version in pyproject.toml using semantic versioning. Supports .dev versions and finalizing dev releases." ) parser.add_argument("file", help="Path to the pyproject.toml file") group = parser.add_mutually_exclusive_group(required=True) - group.add_argument("--bump", choices=["major", "minor", "patch"], help="Type of version bump") + group.add_argument("--bump", choices=["major", "minor", "patch", "finalize"], help="Type of version bump (use 'finalize' to remove the .dev segment from a dev release)") group.add_argument("--set", dest="set_version", help="Set the version explicitly (e.g. 0.2.0 or 0.2.0.dev1)") args = parser.parse_args()