Stop building the APK by hand. Every version tag should automatically produce a signed release APK, and the releases should be consumable by Obtainium so the app updates itself on-device.
Proposal
Gitea Actions workflow triggered on version tags (e.g. v1.0.0):
npm install → npm test → npm run build
npx cap sync android → ./gradlew assembleRelease (JDK 21, API 36 — see AGENTS.md)
Sign with the release keystore (key + passwords via Actions secrets, never in repo)
Attach app-release.apk to the Gitea release, named stably (e.g. mindlist-v1.0.0.apk)
Keep the artifact URL pattern stable so an Obtainium "HTML / direct APK" source keeps working across versions.
Constraints
Debug builds must never be published as releases (anticipated confusion with the launcher-icon issue: release vs debug signing).
The release keystore stays out of git (see AGENTS.md hard rule #3); CI gets it via secrets only.
Acceptance
Pushing a v* tag yields a Gitea release with a signed, installable APK attached — no manual steps
The APK installs over the previous release (same signature) on the test Pixel
Obtainium can track the repo and offers the new version as an update
## Goal
Stop building the APK by hand. Every version tag should automatically produce a signed release APK, and the releases should be consumable by [Obtainium](https://obtainium.imranr.dev/) so the app updates itself on-device.
## Proposal
- Gitea Actions workflow triggered on version tags (e.g. `v1.0.0`):
1. `npm install` → `npm test` → `npm run build`
2. `npx cap sync android` → `./gradlew assembleRelease` (JDK 21, API 36 — see AGENTS.md)
3. Sign with the release keystore (key + passwords via Actions secrets, never in repo)
4. Attach `app-release.apk` to the Gitea release, named stably (e.g. `mindlist-v1.0.0.apk`)
- Keep the artifact URL pattern stable so an Obtainium "HTML / direct APK" source keeps working across versions.
## Constraints
- Debug builds must never be published as releases (anticipated confusion with the launcher-icon issue: release vs debug signing).
- The release keystore stays out of git (see AGENTS.md hard rule #3); CI gets it via secrets only.
## Acceptance
- [ ] Pushing a `v*` tag yields a Gitea release with a signed, installable APK attached — no manual steps
- [ ] The APK installs over the previous release (same signature) on the test Pixel
- [ ] Obtainium can track the repo and offers the new version as an update
lukas
changed title from create release with automatic Build and support for obtainium to Automated signed release builds + Obtainium support2026-10-02 11:35:23 +02:00
v* tag → Gitea Actions builds (npm test → PWA → cap sync → assembleRelease, JDK 21, API 36), signs with the release key, verifies via apksigner + fingerprint pin, and attaches mindlist-<tag>.apk (+ .sha256) to the release. Proven live: test tag produced a signed 3.5 MB APK on a release (cleaned up afterwards), plus green dry-runs.
Secrets in place: KEYSTORE_PASSPHRASE, RELEASE_STORE_PASSWORD, RELEASE_KEY_ALIAS, RELEASE_KEY_PASSWORD (keystore itself travels AES-encrypted in git).
Remaining manual step: in Obtainium, Add App → Gitea → repo URL (+ access token while the repo is private).
Follow-ups if ever needed: versionCode must be bumped in android/app/build.gradle before each release tag (CI enforces this and fails loudly otherwise).
Verified end-to-end ✅
- `v*` tag → Gitea Actions builds (`npm test` → PWA → `cap sync` → `assembleRelease`, JDK 21, API 36), signs with the release key, verifies via `apksigner` + fingerprint pin, and attaches `mindlist-<tag>.apk` (+ `.sha256`) to the release. Proven live: test tag produced a signed 3.5 MB APK on a release (cleaned up afterwards), plus green dry-runs.
- Secrets in place: `KEYSTORE_PASSPHRASE`, `RELEASE_STORE_PASSWORD`, `RELEASE_KEY_ALIAS`, `RELEASE_KEY_PASSWORD` (keystore itself travels AES-encrypted in git).
- Remaining manual step: in Obtainium, Add App → Gitea → repo URL (+ access token while the repo is private).
Follow-ups if ever needed: `versionCode` must be bumped in `android/app/build.gradle` before each release tag (CI enforces this and fails loudly otherwise).
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Goal
Stop building the APK by hand. Every version tag should automatically produce a signed release APK, and the releases should be consumable by Obtainium so the app updates itself on-device.
Proposal
v1.0.0):npm install→npm test→npm run buildnpx cap sync android→./gradlew assembleRelease(JDK 21, API 36 — see AGENTS.md)app-release.apkto the Gitea release, named stably (e.g.mindlist-v1.0.0.apk)Constraints
Acceptance
v*tag yields a Gitea release with a signed, installable APK attached — no manual stepscreate release with automatic Build and support for obtainiumto Automated signed release builds + Obtainium supportVerified end-to-end ✅
v*tag → Gitea Actions builds (npm test→ PWA →cap sync→assembleRelease, JDK 21, API 36), signs with the release key, verifies viaapksigner+ fingerprint pin, and attachesmindlist-<tag>.apk(+.sha256) to the release. Proven live: test tag produced a signed 3.5 MB APK on a release (cleaned up afterwards), plus green dry-runs.KEYSTORE_PASSPHRASE,RELEASE_STORE_PASSWORD,RELEASE_KEY_ALIAS,RELEASE_KEY_PASSWORD(keystore itself travels AES-encrypted in git).Follow-ups if ever needed:
versionCodemust be bumped inandroid/app/build.gradlebefore each release tag (CI enforces this and fails loudly otherwise).