Skip to content

ci: add Google Play publish workflow#41

Merged
AKPWebDesign merged 1 commit into
developfrom
ci/play-store-publish
May 4, 2026
Merged

ci: add Google Play publish workflow#41
AKPWebDesign merged 1 commit into
developfrom
ci/play-store-publish

Conversation

@AKPWebDesign

Copy link
Copy Markdown
Member

Summary

Adds a GitHub Actions workflow that builds a signed AAB and uploads it to Google Play via the Play Developer API.

  • Workflow: .github/workflows/publish-play.yml
  • Triggers:
    • push on tags matching v* (publishes to internal by default)
    • workflow_dispatch with a track input: internal / alpha / beta / production
  • Steps: checkout (full history for androidGitVersion) → JDK 17 (Temurin) → gradle/actions/setup-gradle → decode keystore from base64 secret → ./gradlew :app:bundleProdRelease → upload AAB artifact → r0adkll/upload-google-play@v1.1.5 (pinned by commit SHA)
  • Track: configurable via workflow_dispatch input; defaults to internal on tag pushes
  • Package name: read from the app module's namespace (tech.akpmakes.android.taskkeeper) at workflow runtime

Action sourcing

Per the standing rule "prefer official Actions to community ones": all steps use first-party actions (actions/checkout, actions/setup-java, gradle/actions/setup-gradle, actions/upload-artifact) except the final upload — there is no first-party Google action for the Play Developer API. r0adkll/upload-google-play is the de-facto community standard and is pinned by tag SHA (v1.1.5e738b9d).

All actions pinned to commit SHA with version comments.

Signing config wiring

The existing app/build.gradle only had a debug signing config. Added a parallel releaseApp block (same shape, same Gradle properties — ANDROID_SIGNING_KEY, ANDROID_KEY_PASSWORD, ANDROID_KEY_FILE, ANDROID_STORE_PASSWORD) and wired it into buildTypes.release. All values are passed in via CI env vars (ORG_GRADLE_PROJECT_*); nothing is committed. Locally, builds without ANDROID_SIGNING_KEY set still produce an unsigned release exactly as before.

No tooling upgrades — AGP 8.12.2 / Gradle 8.13 / JDK 17 (matches what AGP 8.x requires) / Groovy DSL all preserved.

Required secrets (configure under repo Settings → Secrets and variables → Actions)

Secret Purpose
ANDROID_KEYSTORE_BASE64 Base64-encoded upload keystore (base64 -w0 upload.keystore)
ANDROID_KEYSTORE_PASSWORD Keystore (store) password
ANDROID_KEY_ALIAS Key alias inside the keystore
ANDROID_KEY_PASSWORD Password for the key entry
PLAY_SERVICE_ACCOUNT_JSON Full JSON for a Play service account with Release Manager permission on this package

Note: Google Play requires the package's first AAB to be uploaded manually before the Developer API will accept uploads. After that one-time bootstrap, this workflow handles every subsequent release.

Test plan

  • Configure the five secrets above
  • Manually run the workflow via workflow_dispatch with track=internal to validate the build and upload path
  • Push a v* tag and confirm the run publishes to the internal track

Refs

- New workflow .github/workflows/publish-play.yml triggers on tag push
  (v*) and workflow_dispatch with a configurable track input.
- Wires a release signing config in app/build.gradle, mirroring the
  existing debug block and reusing the ANDROID_SIGNING_KEY /
  ANDROID_KEY_PASSWORD / ANDROID_KEY_FILE / ANDROID_STORE_PASSWORD
  Gradle property convention, fed via ORG_GRADLE_PROJECT_* env vars.
- Uses pinned official actions (actions/checkout, actions/setup-java,
  gradle/actions/setup-gradle, actions/upload-artifact) and pins
  r0adkll/upload-google-play to its v1.1.5 commit SHA -- there is no
  first-party Google action for the Play Developer API.
- README gains a Release section documenting triggers and the five
  required secrets.
@AKPWebDesign AKPWebDesign merged commit 1efc025 into develop May 4, 2026
@AKPWebDesign AKPWebDesign deleted the ci/play-store-publish branch May 4, 2026 14:02
AKPWebDesign added a commit that referenced this pull request May 4, 2026
)

Two fixes for the failing 'Publish to Google Play' run (#41 follow-up):

1. gradlew was committed with mode 100644, so the runner refused to
   execute it ('./gradlew: Permission denied', exit 126). Set the
   execute bit in the index via 'git update-index --chmod=+x gradlew'
   so checkouts on Linux runners can invoke it directly.

2. The workflow read the store password from a secret named
   ANDROID_KEYSTORE_PASSWORD, but the matching Gradle property in
   app/build.gradle is ANDROID_STORE_PASSWORD. Renamed the workflow
   reference + README documentation to ANDROID_STORE_PASSWORD so all
   five secrets line up 1:1 with the Gradle property names.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant