Skip to content

Commit

Permalink
Changed: Move to semantic versioning for app version and add commit h…
Browse files Browse the repository at this point in the history
…ash and `github` to APK file names

The `versionName` will now follow semantic version `2.0.0` spec in the format `major.minor.patch(-prerelease)(+buildmetadata)`. This will make versioning the prerelease and github debug builds versions easier and follow a spec. The @termux devs should make sure that when bumping `versionName` in `build.gradle` file and when creating a tag for new releases on github that they include the patch number as well, like `v0.1.0` instead of just `v0.1`. The `build.gradle` file and `attach_debug_apks_to_release` workflow will now validate the version as well and the build/attachment will fail if `versionName` does not follow the spec. https://semver.org/spec/v2.0.0.html

APKs released on github for debug build workflows and releases are now referred as `Github` releases as per termux/termux-app@7b10a35f and termux/termux-app@94e01d68, so APK filenames have been modified to include `github` in the filename. The APKs are still debuggable, so that tag remains too.

For github workflows the apk filename format will be `termux-tasker_<current_version>+<last_commit_hash>-github-debug_<arch>.apk`, like `termux-tasker_v0.1.0+xxxxxxxx-github-debug_arm64-v8a.apk` and for github releases it will be `termux-tasker_<release_version>+github-debug_<arch>.apk`, like `termux-tasker_v0.1+github-debug_arm64-v8a.apk`. The `last_commit_hash` will be the first `8` characters of the commit hash. The `<last_commit_hash>-github-debug` will act as `buildmetadata` and will not affect versioning precedence.

For github workflows triggered by `push` and `pull_request` triggers, `<current_version>+<last_commit_hash>` will be used as new `versionName`, like `v0.1.0+xxxxxxxx`. This will make tracking which build a user is using easier and help in resolving issues as well.

The `app/build.gradle` now also supports following `TERMUX_TASKER_` scoped environmental variables and `RELEASE_TAG` variable will not be used anymore since it may conflict with possibly other variables used by users.

- `TERMUX_TASKER_APP_VERSION_NAME` will be used as `versionName` if its set.
- `TERMUX_TASKER_APK_VERSION_TAG` will be used as `termux-tasker_<TERMUX_TASKER_APK_VERSION_TAG>.apk` if its set.
  • Loading branch information
agnostic-apollo committed Jan 8, 2022
1 parent d8b99ba commit 4920bcd
Show file tree
Hide file tree
Showing 4 changed files with 144 additions and 53 deletions.
64 changes: 64 additions & 0 deletions .github/workflows/attach_debug_apk_to_release.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
name: Attach Debug APK To Release

on:
release:
types:
- published

jobs:
attach-apks:
runs-on: ubuntu-latest
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
steps:
- name: Clone repository
uses: actions/checkout@v2
with:
ref: ${{ env.GITHUB_REF }}

- name: Build and attach APK to release
shell: bash {0}
run: |
exit_on_error() {
echo "$1"
echo "Deleting '$RELEASE_VERSION_NAME' release and '$GITHUB_REF' tag"
hub release delete "$RELEASE_VERSION_NAME"
git push --delete origin "$GITHUB_REF"
exit 1
}
echo "Setting vars"
RELEASE_VERSION_NAME="${GITHUB_REF/refs\/tags\//}"
if ! printf "%s" "${RELEASE_VERSION_NAME/v/}" | grep -qP '^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$'; then
exit_on_error "The versionName '${RELEASE_VERSION_NAME/v/}' is not a valid version as per semantic version '2.0.0' spec in the format 'major.minor.patch(-prerelease)(+buildmetadata)'. https://semver.org/spec/v2.0.0.html."
fi
APK_DIR_PATH="./app/build/outputs/apk/debug"
APK_VERSION_TAG="$RELEASE_VERSION_NAME+github-debug"
APK_BASENAME_PREFIX="termux-tasker_$APK_VERSION_TAG"
echo "Building APK for '$RELEASE_VERSION_NAME' release"
export TERMUX_TASKER_APK_VERSION_TAG="$APK_VERSION_TAG" # Used by app/build.gradle
if ! ./gradlew assembleDebug; then
exit_on_error "Build failed for '$RELEASE_VERSION_NAME' release."
fi
echo "Validating APK"
if ! test -f "$APK_DIR_PATH/${APK_BASENAME_PREFIX}.apk"; then
files_found="$(ls "$APK_DIR_PATH")"
exit_on_error "Failed to find built APK at '$APK_DIR_PATH/${APK_BASENAME_PREFIX}.apk'. Files found: "$'\n'"$files_found"
fi
echo "Generating sha25sums file"
if ! (cd "$APK_DIR_PATH"; sha256sum "${APK_BASENAME_PREFIX}.apk" > sha256sums); then
exit_on_error "Generate sha25sums failed for '$RELEASE_VERSION_NAME' release."
fi
echo "Attaching APK to github release"
if ! hub release edit \
-m "" \
-a "$APK_DIR_PATH/${APK_BASENAME_PREFIX}.apk" \
-a "$APK_DIR_PATH/sha256sums" \
"$RELEASE_VERSION_NAME"; then
exit_on_error "Attach APK to release failed for '$RELEASE_VERSION_NAME' release."
fi
32 changes: 0 additions & 32 deletions .github/workflows/attach_debug_apks_to_release.yml

This file was deleted.

72 changes: 59 additions & 13 deletions .github/workflows/debug_build.yml
Original file line number Diff line number Diff line change
@@ -1,20 +1,66 @@
name: Build

on: push
on:
push:
branches:
- master
pull_request:
branches:
- master

jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Clone repository
uses: actions/checkout@v2
- name: Build
run: |
./gradlew assembleDebug
- name: Store generated APK file
uses: actions/upload-artifact@v2
with:
name: termux-tasker
path: |
./app/build/outputs/apk/debug/termux-tasker-debug.apk
./app/build/outputs/apk/debug/output-metadata.json
- name: Clone repository
uses: actions/checkout@v2

- name: Build APK
shell: bash {0}
run: |
exit_on_error() { echo "$1"; exit 1; }
echo "Setting vars"
# Set RELEASE_VERSION_NAME to "<CURRENT_VERSION_NAME>+<last_commit_hash>"
CURRENT_VERSION_NAME_REGEX='\s+versionName "([^"]+)"$'
CURRENT_VERSION_NAME="$(grep -m 1 -E "$CURRENT_VERSION_NAME_REGEX" ./app/build.gradle | sed -r "s/$CURRENT_VERSION_NAME_REGEX/\1/")"
RELEASE_VERSION_NAME="v$CURRENT_VERSION_NAME+${GITHUB_SHA:0:7}" # The "+" is necessary so that versioning precedence is not affected
if ! printf "%s" "${RELEASE_VERSION_NAME/v/}" | grep -qP '^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$'; then
exit_on_error "The versionName '${RELEASE_VERSION_NAME/v/}' is not a valid version as per semantic version '2.0.0' spec in the format 'major.minor.patch(-prerelease)(+buildmetadata)'. https://semver.org/spec/v2.0.0.html."
fi
APK_DIR_PATH="./app/build/outputs/apk/debug"
APK_VERSION_TAG="$RELEASE_VERSION_NAME-github-debug" # Note the "-", GITHUB_SHA will already have "+" before it
APK_BASENAME_PREFIX="termux-tasker_$APK_VERSION_TAG"
# Used by attachment steps later
echo "APK_DIR_PATH=$APK_DIR_PATH" >> $GITHUB_ENV
echo "APK_VERSION_TAG=$APK_VERSION_TAG" >> $GITHUB_ENV
echo "APK_BASENAME_PREFIX=$APK_BASENAME_PREFIX" >> $GITHUB_ENV
echo "Building APK for '$RELEASE_VERSION_NAME' build"
export TERMUX_TASKER_APP_VERSION_NAME="${RELEASE_VERSION_NAME/v/}" # Used by app/build.gradle
export TERMUX_TASKER_APK_VERSION_TAG="$APK_VERSION_TAG" # Used by app/build.gradle
if ! ./gradlew assembleDebug; then
exit_on_error "Build failed for '$RELEASE_VERSION_NAME' build."
fi
echo "Validating APK"
if ! test -f "$APK_DIR_PATH/${APK_BASENAME_PREFIX}.apk"; then
files_found="$(ls "$APK_DIR_PATH")"
exit_on_error "Failed to find built APK at '$APK_DIR_PATH/${APK_BASENAME_PREFIX}.apk'. Files found: "$'\n'"$files_found"
fi
echo "Generating sha25sums file"
if ! (cd "$APK_DIR_PATH"; sha256sum "${APK_BASENAME_PREFIX}.apk" > sha256sums); then
exit_on_error "Generate sha25sums failed for '$RELEASE_VERSION_NAME' release."
fi
- name: Attach files
uses: actions/upload-artifact@v2
with:
name: ${{ env.APK_BASENAME_PREFIX }}
path: |
${{ env.APK_DIR_PATH }}/${{ env.APK_BASENAME_PREFIX }}.apk
${{ env.APK_DIR_PATH }}/sha256sums
${{ env.APK_DIR_PATH }}/output-metadata.json
29 changes: 21 additions & 8 deletions app/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,18 @@ apply plugin: 'com.android.application'

android {
compileSdkVersion project.properties.compileSdkVersion.toInteger()
def appVersionName = System.getenv("TERMUX_TASKER_APP_VERSION_NAME") ?: ""
def apkVersionTag = System.getenv("TERMUX_TASKER_APK_VERSION_TAG") ?: ""

defaultConfig {
applicationId "com.termux.tasker"
minSdkVersion project.properties.minSdkVersion.toInteger()
targetSdkVersion project.properties.targetSdkVersion.toInteger()
versionCode 5
versionName "0.5"
testInstrumentationRunner 'androidx.test.runner.AndroidJUnitRunner'
versionName "0.5.0"

if (appVersionName) versionName = appVersionName
validateVersionName(versionName)

manifestPlaceholders.TERMUX_PACKAGE_NAME = "com.termux"
manifestPlaceholders.TERMUX_APP_NAME = "Termux"
Expand Down Expand Up @@ -45,8 +50,9 @@ android {
applicationVariants.all { variant ->
variant.outputs.all { output ->
if (variant.buildType.name == "debug") {
def releaseTag = System.getenv("RELEASE_TAG")
outputFileName = new File("termux-tasker" + (releaseTag ? "-" + releaseTag : "") + "-debug.apk")
outputFileName = new File("termux-tasker_" + (apkVersionTag ? apkVersionTag : "debug") + ".apk")
} else if (variant.buildType.name == "release") {
outputFileName = new File("termux-tasker_" + (apkVersionTag ? apkVersionTag : "release") + ".apk")
}
}
}
Expand All @@ -69,11 +75,18 @@ dependencies {
// Use if below libraries are published locally by termux-app with `./gradlew publishReleasePublicationToMavenLocal` and used with `mavenLocal()`.
// If updates are done, republish there and sync project with gradle files here
// https://github.com/termux/termux-app/wiki/Termux-Libraries
//implementation 'com.termux:termux-shared:0.117'
// implementation 'com.termux:termux-shared:0.117'
}

task versionName {
doLast {
print android.defaultConfig.versionName
}
doLast {
print android.defaultConfig.versionName
}
}

def validateVersionName(String versionName) {
// https://semver.org/spec/v2.0.0.html#is-there-a-suggested-regular-expression-regex-to-check-a-semver-string
// ^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$
if (!java.util.regex.Pattern.matches("^(0|[1-9]\\d*)\\.(0|[1-9]\\d*)\\.(0|[1-9]\\d*)(?:-((?:0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\\.(?:0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\\+([0-9a-zA-Z-]+(?:\\.[0-9a-zA-Z-]+)*))?\$", versionName))
throw new GradleException("The versionName '" + versionName + "' is not a valid version as per semantic version '2.0.0' spec in the format 'major.minor.patch(-prerelease)(+buildmetadata)'. https://semver.org/spec/v2.0.0.html.")
}

0 comments on commit 4920bcd

Please sign in to comment.