Add a setting to read additional config files from any other config
[xxxterm.git] / release.sh
blobcfbebb3a3a82b364116b3ed9bee5d4edc0947c90
1 #!/bin/sh
3 # Prepares a release:
4 # - Bumps version according to specified level (major, minor, or patch)
5 # - Updates all necessary headers with new version
6 # - Commits the changes
7 # - Tags the release
8 # - Creates a release tarball
10 PROJECT=xxxterm
11 PROJECT_UC=$(echo $PROJECT | tr '[:lower:]' '[:upper:]')
12 SCRIPT=$(basename $0)
13 HEADER=version.h
15 # verify params
16 if [ $# -lt 1 ]; then
17 echo "usage: $SCRIPT {major | minor | patch}"
18 exit 1
21 report_err()
23 echo "$SCRIPT: error: $1" 1>&2
24 exit 1
28 cd "$(dirname $0)"
30 # verify header exists
31 if [ ! -f "$HEADER" ]; then
32 report_err "$HEADER does not exist"
35 # verify valid release type
36 RTYPE="$1"
37 if [ "$RTYPE" != "major" -a "$RTYPE" != "minor" -a "$RTYPE" != "patch" ]; then
38 report_err "release type must be major, minor, or patch"
41 # verify git is available
42 if ! type git >/dev/null 2>&1; then
43 report_err "unable to find 'git' in the system path"
46 # verify the git repository is on the master branch
47 BRANCH=$(git branch | grep '\*' | cut -c3-)
48 if [ "$BRANCH" != "master" ]; then
49 report_err "git repository must be on the master branch"
52 # verify there are no uncommitted modifications prior to release modifications
53 NUM_MODIFIED=$(git diff 2>/dev/null | wc -l | sed 's/^[ \t]*//')
54 NUM_STAGED=$(git diff --cached 2>/dev/null | wc -l | sed 's/^[ \t]*//')
55 if [ "$NUM_MODIFIED" != "0" -o "$NUM_STAGED" != "0" ]; then
56 report_err "the working directory contains uncommitted modifications"
59 # get version
60 PAT_PREFIX="(^#define[[:space:]]+${PROJECT_UC}"
61 PAT_SUFFIX='[[:space:]]+)[0-9]+$'
62 MAJOR=$(egrep "${PAT_PREFIX}_MAJOR${PAT_SUFFIX}" $HEADER | awk '{print $3}')
63 MINOR=$(egrep "${PAT_PREFIX}_MINOR${PAT_SUFFIX}" $HEADER | awk '{print $3}')
64 PATCH=$(egrep "${PAT_PREFIX}_PATCH${PAT_SUFFIX}" $HEADER | awk '{print $3}')
65 if [ -z "$MAJOR" -o -z "$MINOR" -o -z "$PATCH" ]; then
66 report_err "unable to get version from $HEADER"
69 # bump version according to level
70 if [ "$RTYPE" = "major" ]; then
71 MAJOR=$(expr $MAJOR + 1)
72 MINOR=0
73 PATCH=0
74 elif [ "$RTYPE" = "minor" ]; then
75 MINOR=$(expr $MINOR + 1)
76 PATCH=0
77 elif [ "$RTYPE" = "patch" ]; then
78 PATCH=$(expr $PATCH + 1)
80 PROJ_VER="$MAJOR.$MINOR.$PATCH"
82 # update header with new version
83 sed -E "
84 s/${PAT_PREFIX}_MAJOR${PAT_SUFFIX}/\1${MAJOR}/;
85 s/${PAT_PREFIX}_MINOR${PAT_SUFFIX}/\1${MINOR}/;
86 s/${PAT_PREFIX}_PATCH${PAT_SUFFIX}/\1${PATCH}/;
87 " <"$HEADER" >"${HEADER}.tmp"
89 # apply changes
90 mv "${HEADER}.tmp" "$HEADER"
92 # commit and tag
93 TAG="${PROJECT_UC}_${MAJOR}_${MINOR}_${PATCH}"
94 git commit -am "Prepare for release ${PROJ_VER}." ||
95 report_err "unable to commit changes"
96 git tag -a "$TAG" -m "Release ${PROJ_VER}" || report_err "unable to create tag"
98 # create temp working space and copy repo over
99 TD=$(mktemp -d /tmp/release.XXXXXXXXXX)
100 if [ ! -d "$TD" ]; then
101 report_err "unable to create temp directory"
103 RELEASE_DIR="$PROJECT-$PROJ_VER"
104 RELEASE_TAR="$PROJECT-$PROJ_VER.tgz"
105 git clone . "$TD/$RELEASE_DIR" ||
106 report_err "unable to copy to $TD/$RELEASE_DIR"
108 # cleanup repository files
109 cd "$TD"
110 if [ -d "$RELEASE_DIR" -a -d "$RELEASE_DIR/.git" ]; then
111 rm -rf "$RELEASE_DIR/.git"
113 if [ -d "$RELEASE_DIR" -a -f "$RELEASE_DIR/.gitignore" ]; then
114 rm -f "$RELEASE_DIR/.gitignore"
117 # make snap
118 tar -zcf "$RELEASE_TAR" "$RELEASE_DIR" ||
119 report_err "unable to create $RELEASE_TAR"
122 echo "Release tarball:"
123 echo " $TD/$RELEASE_TAR"
124 echo ""
125 echo "If everything is accurate, use the following command to push the changes:"
126 echo " git push --tags origin master"