From a3c2271b484f5be10eb078b075349c4ce262a184 Mon Sep 17 00:00:00 2001 From: Christian Sidak Date: Thu, 16 Apr 2026 21:39:11 -0700 Subject: [PATCH] Fix release script skipping version bump for lockfile-only changes has_changes() filtered changed files to only .py and .ts suffixes, so packages with only lockfile updates (e.g. uv.lock from dependabot) were never version-bumped. Remove the suffix filter so any file change in a package directory triggers the CalVer bump. Closes #3870 Co-Authored-By: Claude Opus 4.6 (1M context) --- scripts/release.py | 6 ++-- scripts/test_release.py | 72 +++++++++++++++++++++++++++++++++++++++++ 2 files changed, 75 insertions(+), 3 deletions(-) create mode 100644 scripts/test_release.py diff --git a/scripts/release.py b/scripts/release.py index e4ce1274c3..b4ac148236 100755 --- a/scripts/release.py +++ b/scripts/release.py @@ -112,9 +112,9 @@ def has_changes(path: Path, git_hash: GitHash) -> bool: text=True, ) - changed_files = [Path(f) for f in output.stdout.splitlines()] - relevant_files = [f for f in changed_files if f.suffix in [".py", ".ts"]] - return len(relevant_files) >= 1 + changed_files = output.stdout.splitlines() + + return len(changed_files) >= 1 except subprocess.CalledProcessError: return False diff --git a/scripts/test_release.py b/scripts/test_release.py new file mode 100644 index 0000000000..9e958bb520 --- /dev/null +++ b/scripts/test_release.py @@ -0,0 +1,72 @@ +"""Tests for release.py has_changes function.""" + +import subprocess +import tempfile +from pathlib import Path + +from release import has_changes, GitHash + + +def _run(cmd: str, cwd: Path) -> None: + subprocess.run(cmd.split(), cwd=cwd, check=True, capture_output=True) + + +def _init_repo(tmp: Path) -> GitHash: + """Create a git repo with an initial commit and return its hash.""" + _run("git init", tmp) + _run("git config user.email test@test.com", tmp) + _run("git config user.name Test", tmp) + (tmp / "README.md").write_text("init") + _run("git add -A", tmp) + _run("git commit -m init", tmp) + result = subprocess.run( + ["git", "rev-parse", "HEAD"], + cwd=tmp, check=True, capture_output=True, text=True, + ) + return GitHash(result.stdout.strip()) + + +def test_no_changes(): + with tempfile.TemporaryDirectory() as tmp: + tmp = Path(tmp) + git_hash = _init_repo(tmp) + assert has_changes(tmp, git_hash) is False + + +def test_py_file_change(): + with tempfile.TemporaryDirectory() as tmp: + tmp = Path(tmp) + git_hash = _init_repo(tmp) + (tmp / "server.py").write_text("print('hi')") + _run("git add -A", tmp) + _run("git commit -m add-py", tmp) + assert has_changes(tmp, git_hash) is True + + +def test_lockfile_change(): + """Lockfile-only changes must be detected -- this was the bug.""" + with tempfile.TemporaryDirectory() as tmp: + tmp = Path(tmp) + git_hash = _init_repo(tmp) + (tmp / "uv.lock").write_text("lockfile content") + _run("git add -A", tmp) + _run("git commit -m add-lock", tmp) + assert has_changes(tmp, git_hash) is True + + +def test_toml_change(): + with tempfile.TemporaryDirectory() as tmp: + tmp = Path(tmp) + git_hash = _init_repo(tmp) + (tmp / "pyproject.toml").write_text("[project]\nname='x'") + _run("git add -A", tmp) + _run("git commit -m add-toml", tmp) + assert has_changes(tmp, git_hash) is True + + +if __name__ == "__main__": + test_no_changes() + test_py_file_change() + test_lockfile_change() + test_toml_change() + print("All tests passed.")