Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 46 additions & 0 deletions .github/workflows/play-listing.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
name: Play store listing

# Pushes fastlane/metadata/android to Google Play without a release: the title, the
# descriptions, the graphics and the screenshots. A tagged release already uploads all of
# this with the bundle (release.yml); this is for correcting the listing between releases.
#
# Run it from the Actions tab. It reads the branch it is run on, so run it on main.
on:
workflow_dispatch:

permissions:
contents: read

jobs:
listing:
name: Upload store listing
runs-on: ubuntu-24.04
environment: play

steps:
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1

- uses: ruby/setup-ruby@de492cf36cbab201753d720ce4f4e336cd688c94 # v1.336.0
with:
bundler-cache: true

# Release notes belong to a build, so they are left to the release upload.
#
# supply anchors even a listing-only edit to a release: it looks one up on the track,
# and fails if it finds none (the default track is production) or several. So it is
# pointed at the testing track and at the versionCode this branch was released as.
- name: Upload store listing
env:
SUPPLY_JSON_KEY_DATA: ${{ secrets.PLAY_SERVICE_ACCOUNT_JSON }}
TRACK: ${{ vars.PLAY_TRACK || 'alpha' }}
run: |
VERSION_CODE=$(grep -oP 'versionCode\s*=\s*\K\d+' app/build.gradle.kts)
bundle exec fastlane supply \
--package_name com.markreader \
--track "$TRACK" \
--version_code "$VERSION_CODE" \
--metadata_path fastlane/metadata/android \
--sync_image_upload true \
--skip_upload_apk true \
--skip_upload_aab true \
--skip_upload_changelogs true
27 changes: 27 additions & 0 deletions .github/workflows/release-checks.yml
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,33 @@ jobs:
echo "--- contents ---"
cat "$FILE"

# Google Play rejects the whole upload when one field is over its limit, and that
# upload runs only after the tag. Characters, not bytes: `wc -m` under a UTF-8 locale.
# supply sends a file as it is, so line breaks count; only the final one is dropped.
- name: Store listing fits Google Play's limits
env:
LC_ALL: C.UTF-8
VERSION_CODE: ${{ steps.pr.outputs.version_code }}
run: |
FAIL=0
check() {
[ -f "$1" ] || return 0
LEN=$(printf '%s' "$(cat "$1")" | wc -m)
if [ "$LEN" -gt "$2" ]; then
echo "❌ $1 is $LEN characters; Google Play allows $2"
FAIL=1
else
echo "✅ $1: $LEN / $2"
fi
}
for DIR in fastlane/metadata/android/*/; do
check "${DIR}title.txt" 30
check "${DIR}short_description.txt" 80
check "${DIR}full_description.txt" 4000
check "${DIR}changelogs/${VERSION_CODE}.txt" 500
done
exit $FAIL

# The table is normally kept current by translation-table.yml's bot PR; this
# catches a release cut while that PR is still open.
- uses: actions/setup-java@b843ebf9b913146b38da2eaa7aeddf76074ae1ad # v6.1.0
Expand Down
62 changes: 60 additions & 2 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,10 @@ jobs:
- name: Decode keystore
run: echo "${{ secrets.KEYSTORE_FILE }}" | base64 -d > keystore.jks

- name: Build signed release APK
run: ./gradlew assembleRelease
# One Gradle run, one R8 pass: the APK (GitHub, F-Droid's comparison) and the bundle
# (Google Play) come from the same minified code, so they share a mapping file.
- name: Build signed release APK and bundle
run: ./gradlew assembleRelease bundleRelease
env:
KEYSTORE_PATH: ${{ github.workspace }}/keystore.jks
KEYSTORE_PASSWORD: ${{ secrets.KEYSTORE_PASSWORD }}
Expand All @@ -53,3 +55,59 @@ jobs:
name: ${{ github.ref_name }}
generate_release_notes: true
files: app/build/outputs/apk/release/mark-reader-${{ github.ref_name }}.apk

- name: Keep the bundle for the Play upload
uses: actions/upload-artifact@cf430e030ddbb5b0abf93d22962f4752f3646cd9 # v7.0.2
with:
name: play-bundle
path: |
app/build/outputs/bundle/release/*.aab
app/build/outputs/mapping/release/mapping.txt
if-no-files-found: error
retention-days: 7

# A separate job so a Play failure never holds back the GitHub Release, and so the service
# account key is only exposed here. The `play` environment can require an approval first.
play:
name: Upload to Google Play
needs: release
runs-on: ubuntu-24.04
environment: play
permissions:
contents: read

steps:
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1

- uses: actions/download-artifact@9000827ccba6bdab643e8b6fd33ac0654aef8333 # v8.0.2
with:
name: play-bundle
path: play-bundle

- uses: ruby/setup-ruby@de492cf36cbab201753d720ce4f4e336cd688c94 # v1.336.0
with:
bundler-cache: true

# Uploads the bundle to the testing track along with everything under
# fastlane/metadata/android: the listing text, the graphics, the screenshots and
# changelogs/<versionCode>.txt as the release notes. The same files F-Droid reads at
# this tag, so both stores describe the same build.
#
# PLAY_TRACK is a repository variable; `alpha` is Play's default closed testing track.
# A custom closed track is addressed by its name.
- name: Upload bundle and store listing
env:
SUPPLY_JSON_KEY_DATA: ${{ secrets.PLAY_SERVICE_ACCOUNT_JSON }}
TRACK: ${{ vars.PLAY_TRACK || 'alpha' }}
run: |
AAB=$(find play-bundle -name '*.aab' | head -n 1)
MAPPING=$(find play-bundle -name 'mapping.txt' | head -n 1)
bundle exec fastlane supply \
--package_name com.markreader \
--track "$TRACK" \
--release_status completed \
--aab "$AAB" \
--mapping "$MAPPING" \
--metadata_path fastlane/metadata/android \
--sync_image_upload true \
--skip_upload_apk true
1 change: 1 addition & 0 deletions .ruby-version
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
3.3
5 changes: 5 additions & 0 deletions Gemfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
source "https://rubygems.org"

# Uploads the bundle and the store listing to Google Play. Pinned exactly; the lockfile pins
# the rest.
gem "fastlane", "2.241.2"
Loading
Loading