mirror of
https://github.com/doolijb/serene-pub.git
synced 2026-07-20 21:23:26 +00:00
140 lines
5.7 KiB
YAML
140 lines
5.7 KiB
YAML
name: Build Android APK
|
|
|
|
on:
|
|
push:
|
|
tags:
|
|
- "v*.*.*"
|
|
- "v*.*.*-dev"
|
|
- "v*.*.*-alpha"
|
|
- "v*.*.*-beta"
|
|
- "v*.*.*-pr-*"
|
|
- "v*.*.*-rc-*"
|
|
|
|
jobs:
|
|
build-android:
|
|
name: Build Android APK
|
|
runs-on: ubuntu-latest
|
|
steps:
|
|
- name: Checkout code
|
|
uses: actions/checkout@v4
|
|
|
|
# Mirrors release.yml's own prerelease detection exactly, so this
|
|
# workflow's APK lands as an asset on the same tagged release with
|
|
# a prerelease flag that never disagrees with the main build.
|
|
- name: Determine prerelease status
|
|
id: release_info
|
|
shell: bash
|
|
run: |
|
|
TAG="${{ github.ref_name }}"
|
|
VERSION="${TAG#v}"
|
|
|
|
if [[ "$VERSION" =~ ^([0-9]+\.[0-9]+\.[0-9]+)(-(.+))?$ ]]; then
|
|
SUFFIX="${BASH_REMATCH[3]}"
|
|
if [ -z "$SUFFIX" ] || [ "$SUFFIX" = "beta" ]; then
|
|
IS_PRERELEASE="false"
|
|
else
|
|
IS_PRERELEASE="true"
|
|
fi
|
|
else
|
|
IS_PRERELEASE="true"
|
|
fi
|
|
|
|
echo "version=$VERSION" >> $GITHUB_OUTPUT
|
|
echo "is_prerelease=$IS_PRERELEASE" >> $GITHUB_OUTPUT
|
|
echo "Version: $VERSION"
|
|
echo "Is Pre-release: $IS_PRERELEASE"
|
|
|
|
- name: Set up Node.js
|
|
uses: actions/setup-node@v4
|
|
with:
|
|
node-version: "24"
|
|
|
|
- name: Set up JDK 17
|
|
uses: actions/setup-java@v4
|
|
with:
|
|
distribution: "temurin"
|
|
java-version: "17"
|
|
|
|
- name: Install dependencies
|
|
run: |
|
|
node -e "const fs = require('fs'); try { fs.unlinkSync('package-lock.json'); } catch (e) { /* ignore */ }"
|
|
for i in 1 2 3; do npm install --fetch-retries=5 --fetch-retry-mintimeout=20000 --fetch-retry-maxtimeout=120000 && break || sleep 15; done
|
|
|
|
- name: Prepare SvelteKit
|
|
run: npx @sveltejs/kit sync
|
|
|
|
- name: Build SvelteKit app
|
|
run: npm run build
|
|
|
|
- name: Prepare production dependencies
|
|
run: |
|
|
npm install --omit=dev
|
|
npm rebuild
|
|
|
|
- name: Prepare Android assets
|
|
run: node scripts/build-android.js
|
|
|
|
- name: Decode keystore
|
|
env:
|
|
KEYSTORE_BASE64: ${{ secrets.ANDROID_KEYSTORE_BASE64 }}
|
|
run: |
|
|
if [ -n "$KEYSTORE_BASE64" ]; then
|
|
echo "$KEYSTORE_BASE64" | base64 -d > android/app/release.keystore
|
|
echo "Keystore decoded successfully"
|
|
else
|
|
echo "No keystore configured, building an unsigned APK"
|
|
fi
|
|
|
|
- name: Make gradlew executable
|
|
run: chmod +x android/gradlew
|
|
|
|
- name: Build Release APK
|
|
env:
|
|
KEYSTORE_PASSWORD: ${{ secrets.ANDROID_KEYSTORE_PASSWORD }}
|
|
KEY_ALIAS: ${{ secrets.ANDROID_KEY_ALIAS }}
|
|
KEY_PASSWORD: ${{ secrets.ANDROID_KEY_PASSWORD }}
|
|
working-directory: android
|
|
run: |
|
|
# Only set KEYSTORE_FILE if the keystore was actually decoded —
|
|
# build.gradle treats its mere presence as "sign this build", so
|
|
# an unconditionally-set env var would make it try to sign with a
|
|
# keystore that doesn't exist whenever the secrets aren't configured.
|
|
# Gradle's file() in app/build.gradle resolves relative to the
|
|
# app/ project directory, so this must be a bare filename, not a
|
|
# path relative to this step's android/ working directory.
|
|
if [ -f "app/release.keystore" ]; then
|
|
export KEYSTORE_FILE=release.keystore
|
|
fi
|
|
./gradlew assembleRelease
|
|
|
|
# Signed and unsigned release builds produce differently-named APKs
|
|
# (app-release.apk vs. app-release-unsigned.apk) — this always
|
|
# results in exactly one renamed file in dist/, regardless of which
|
|
# case occurred, so exactly one APK ever reaches the release.
|
|
- name: Rename APK
|
|
id: rename_apk
|
|
run: |
|
|
VERSION="${{ steps.release_info.outputs.version }}"
|
|
mkdir -p dist
|
|
SRC=""
|
|
if [ -f "android/app/build/outputs/apk/release/app-release.apk" ]; then
|
|
SRC="android/app/build/outputs/apk/release/app-release.apk"
|
|
elif [ -f "android/app/build/outputs/apk/release/app-release-unsigned.apk" ]; then
|
|
SRC="android/app/build/outputs/apk/release/app-release-unsigned.apk"
|
|
else
|
|
echo "Error: no release APK found in android/app/build/outputs/apk/release/"
|
|
ls -la android/app/build/outputs/apk/release/ || true
|
|
exit 1
|
|
fi
|
|
DEST="dist/serene-pub-${VERSION}-android.apk"
|
|
cp "$SRC" "$DEST"
|
|
echo "apk_path=$DEST" >> $GITHUB_OUTPUT
|
|
echo "Renamed $SRC -> $DEST"
|
|
|
|
- name: Upload to Release
|
|
uses: softprops/action-gh-release@v2
|
|
with:
|
|
files: ${{ steps.rename_apk.outputs.apk_path }}
|
|
prerelease: ${{ steps.release_info.outputs.is_prerelease }}
|
|
env:
|
|
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|