Last active
June 18, 2025 11:31
-
-
Save slhck/362b234b85b41c42681c937e912fb113 to your computer and use it in GitHub Desktop.
Simple uv-based release script
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env bash | |
# | |
# Release the project and bump version number in the process. | |
# | |
# To set up the project, make sure you have in pyproject.toml: | |
# | |
# [project] | |
# name = "foo-bar" | |
# version = "2.10.0" | |
# ... | |
# [project.scripts] | |
# foo_bar = "foo_bar.__main__:main" | |
# # make uv build the project before running | |
# [build-system] | |
# requires = ["uv_build>=0.7.13,<0.8.0"] | |
# build-backend = "uv_build" | |
# | |
# # set the module path to the root of the project instead of "src" (default) | |
# [tool.uv.build-backend] | |
# module-name = "foo_bar" | |
# module-root = "" | |
# | |
# And in `foo_bar/__init__.py`: | |
# | |
# from importlib.metadata import version | |
# | |
# __version__ = version("foo-bar") | |
set -e | |
cd "$(dirname "$0")" | |
FORCE=false | |
usage() { | |
echo "Usage: $0 [options] VERSION" | |
echo | |
echo "VERSION:" | |
echo " major: bump major version number" | |
echo " minor: bump minor version number" | |
echo " patch: bump patch version number" | |
echo | |
echo "Options:" | |
echo " -f, --force: force release" | |
echo " -h, --help: show this help message" | |
exit 1 | |
} | |
# parse args | |
while [ "$#" -gt 0 ]; do | |
case "$1" in | |
-f | --force) | |
FORCE=true | |
shift | |
;; | |
-h | --help) | |
usage | |
;; | |
*) | |
break | |
;; | |
esac | |
done | |
# check if version is specified | |
if [ "$#" -ne 1 ]; then | |
usage | |
fi | |
if [ "$1" != "major" ] && [ "$1" != "minor" ] && [ "$1" != "patch" ]; then | |
usage | |
fi | |
# check if git is clean and force is not enabled | |
if ! git diff-index --quiet HEAD -- && [ "$FORCE" = false ]; then | |
echo "Error: git is not clean. Please commit all changes first." | |
exit 1 | |
fi | |
if ! command -v uv &> /dev/null; then | |
echo "Error: uv is not installed. Please install uv from https://docs.astral.sh/uv/" | |
exit 1 | |
fi | |
echo "Would bump version:" | |
uv version --bump "$1" --dry-run | |
# prompt for confirmation | |
if [ "$FORCE" = false ]; then | |
read -p "Do you want to release? [yY] " -n 1 -r | |
echo | |
else | |
REPLY="y" | |
fi | |
echo | |
if [[ $REPLY =~ ^[Yy]$ ]]; then | |
# replace version number | |
uv version --bump "$1" | |
new_version=$(uv version --short) | |
# commit changes | |
git add pyproject.toml uv.lock | |
git commit -m "bump version to $new_version" | |
git tag -a "v$new_version" -m "v$new_version" | |
# generate changelog | |
uvx --with pystache gitchangelog > CHANGELOG.md | |
git add CHANGELOG.md | |
git commit --no-verify --amend --no-edit | |
git tag -a -f -m "v$new_version" "v$new_version" | |
# push changes | |
git push origin master | |
git push origin "v$new_version" | |
else | |
echo "Aborted." | |
exit 1 | |
fi |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment