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
51 changes: 33 additions & 18 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -312,31 +312,46 @@ jobs:
run: |
echo "${{ secrets.PLAYSTORE_CREDENTIALS_BASE64 }}" | base64 --decode > "${{ runner.temp }}/playstore-credentials.json"

- name: Set up Java
uses: actions/setup-java@v5
# `fastforge publish --targets playstore` only uploads the bundle and
# names the track release; it never sends release notes or the store
# listing, which is why the fastlane changelogs never reached Play.
# `fastlane supply` uploads the bundle *and* the metadata tree in one
# Play edit, so the listing can never drift from the binary it ships.
- name: Set up Ruby
uses: ruby/setup-ruby@v1
with:
distribution: temurin
java-version: '17'
ruby-version: '3.3'

- name: Set up Flutter
uses: subosito/flutter-action@v2
with:
flutter-version: '3.41.7'
cache: true
- name: Install fastlane
run: gem install fastlane -N -v 2.238.0

- name: Install Fastforge
run: dart pub global activate fastforge
- name: Install Pillow
run: pip install --disable-pip-version-check pillow

# The committed tree targets F-Droid, which has none of Play's limits on
# release-note length or screenshot aspect ratio. See the script.
- name: Prepare Play Store metadata
run: |
python3 tool/prepare_play_metadata.py \
fastlane/metadata/android \
"${{ runner.temp }}/play-metadata"

- name: Publish to Play Store
env:
PLAYSTORE_CREDENTIALS: ${{ runner.temp }}/playstore-credentials.json
run: |
set -e
AAB_PATH=$(find artifacts/aab -name "*.aab" | head -1)
fastforge publish \
--path "$AAB_PATH" \
--targets playstore \
--playstore-package-name org.openpatch.classi \
--playstore-track production
if [ -z "$AAB_PATH" ]; then
echo "ERROR: no .aab found in artifacts/aab" >&2
exit 1
fi
fastlane supply \
--package_name org.openpatch.classi \
--aab "$AAB_PATH" \
--track production \
--release_status completed \
--json_key "${{ runner.temp }}/playstore-credentials.json" \
--metadata_path "${{ runner.temp }}/play-metadata" \
--sync_image_upload true

release:
name: Create GitHub Release
Expand Down
57 changes: 53 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -161,14 +161,57 @@ Or run all platforms at once using the project release config:
fastforge release --name release
```

## Store metadata

`fastlane/metadata/android/` holds the store listing — title, descriptions,
icon, phone screenshots and one release-notes file per version code
(`en-US/changelogs/46.txt` belongs to the build whose `version_code.txt` said
`46`). F-Droid reads this tree straight from the repository; the Play Store
gets it from the `release.yml` workflow via `fastlane supply`.

The tree is authored for F-Droid, which accepts anything. Google Play does not:
release notes are capped at 500 characters, screenshots may not have an alpha
channel, and their longest side may be at most twice the shortest — the
1080x2424 phone screenshots here are 1:2.24 and would be rejected. Rather than
degrade the F-Droid assets, `tool/prepare_play_metadata.py` writes a normalised
copy that only Play sees:

```bash
python3 tool/prepare_play_metadata.py fastlane/metadata/android build/play-metadata
```

It trims release notes on a bullet boundary, drops the alpha channel and
letterboxes screenshots by repeating their edge pixels (so padding continues
the app bar instead of adding black bars), and fails loudly on anything
hand-written that Play would reject, such as a title over 30 characters.

Because the whole tree is uploaded on every release, the repository is the
source of truth: edits made directly in the Play Console are overwritten on the
next tag. To see what would be sent without committing anything to Play, add
`--validate_only true`:

```bash
fastlane supply --package_name org.openpatch.classi \
--metadata_path build/play-metadata \
--skip_upload_aab true --skip_upload_apk true --skip_upload_changelogs true \
--json_key playstore-credentials.json --validate_only true
```

(Release notes are skipped there because they attach to a release that only
exists once the bundle is uploaded.)

German release notes fall back to `de-DE/changelogs/default.txt`, since the
generated changelog is English only. Add `de-DE/changelogs/<version code>.txt`
to give a release proper German notes.

## Contributing

See [CONTRIBUTING.md](CONTRIBUTING.md) for local setup, pull request
expectations, and release hygiene.

## GitHub Actions

Four workflows are included:
Five workflows are included:

- `ci.yml` — runs on every push to `main`/`master` and on pull requests. It
installs dependencies, runs Drift code generation, analyzes the code, and
Expand All @@ -192,11 +235,17 @@ Four workflows are included:

Android PR builds use the application ID `org.openpatch.classi.pr` so they
can be installed alongside the production app without overwriting it.
- `changelog.yml` — on every push to `main`, regenerates the unreleased section
with `git-cliff` into `fastlane/metadata/android/en-US/changelogs/<next
version code>.txt` and commits it, so the next release already carries its
notes for both stores. See [Store metadata](#store-metadata).
- `release.yml` — triggered by version tags (`v*`). It generates a changelog
with `git-cliff`, commits an updated `CHANGELOG.md`, builds release artifacts
for Android (APK), Linux (AppImage), macOS (DMG), and Windows (EXE installer)
using [Fastforge](https://fastforge.dev/), and publishes a GitHub Release with
all artifacts attached.
for Android (APK and AAB), Linux (AppImage), macOS (DMG), and Windows (EXE
installer) using [Fastforge](https://fastforge.dev/), publishes a GitHub
Release with all artifacts attached, and uploads the AAB to the Play Store
production track together with the
[store metadata](#store-metadata) using `fastlane supply`.

## Development support

Expand Down
4 changes: 4 additions & 0 deletions fastlane/metadata/android/de-DE/changelogs/default.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
Fehlerbehebungen und Verbesserungen.

Die vollständigen Änderungen dieser Version stehen unter
https://github.com/openpatch/classi/releases
Loading