| name | local-android-build-movieplanner-mobile |
| description | Build movieplanner-mobile Android locally when the user asks for AAB/APK, local build, or when EAS build is unavailable/limited. Use for “собери локально”, “локально собирай”, “AAB”, “APK”, “EAS лимит”, “Expo limit”, “сборка приложения” in Movie Planner. |
Local Android Build — movieplanner-mobile
Rule
If EAS fails because of Expo Free Plan limits or the user asks to build locally, do not stop at the EAS error. Build Android locally from movieplanner-mobile.
Before any build: read .cursor/skills/local-build-queue/SKILL.md. One build at a time on this Mac — never parallel iOS + Android or two gradle/eas local builds.
After every local build, run ./scripts/copy-release-artifacts.sh so the user gets artifacts only in project root — see mobile skill movieplanner-mobile/.cursor/skills/local-build-artifacts/SKILL.md.
Paths
- Bot repo:
/Users/nikitazaporohzets/Desktop/Кино/movie_planner_bot
- Mobile repo:
/Users/nikitazaporohzets/Desktop/Кино/movieplanner-mobile
Canonical output (report these to the user)
| Artifact | Path |
|---|
| Play AAB | movieplanner-mobile/MoviePlanner-release.aab |
| RuStore AAB | movieplanner-mobile/MoviePlanner-RuStore-release.aab |
| APK | movieplanner-mobile/MoviePlanner-release.apk |
RuStore — отдельная сборка: ./scripts/build-rustore-aab.sh → MoviePlanner-RuStore-release.aab. См. movieplanner-mobile/.cursor/skills/local-rustore-aab-build/SKILL.md.
Do not leave build-*.aab, builds/*.aab, or android/app-release.aab as the final deliverable.
Play Store signing (mandatory for AAB upload)
NEVER upload AAB signed with debug keystore. Play expects upload key SHA1:
58:68:C5:8A:3B:57:12:F7:A7:DA:0C:D3:2D:D7:30:AC:07:1C:7F:F3
Before bundleRelease for Play:
- Sync upload keystore from EAS (
com.movie_planner credentials):
export EXPO_TOKEN=$(grep '^EXPO_TOKEN=' ../movie_planner_bot/.env | cut -d= -f2-)
./scripts/sync-android-upload-keystore.sh
- Confirm
android/app/build.gradle uses signingConfigs.release with MYAPP_UPLOAD_* from android/gradle.properties.
- Verify SHA1 after build (see mobile skill
movieplanner-mobile/.cursor/skills/android-play-signing/SKILL.md).
Keystore file (local, gitignored): android/app/movie-planner-upload.keystore
If EAS limits block cloud build and keystore sync fails, stop and fix credentials — do not ship debug-signed AAB.
Build order (Play AAB — обязательно)
Одна команда (versionCode из EAS + keystore + AAB + copy):
cd movieplanner-mobile
./scripts/build-play-aab.sh
Никогда не отдавать пользователю AAB после голого ./gradlew bundleRelease без ensure-android-version-for-play.sh — иначе versionCode 18 и Play отклоняет.
Учёт версий Play: movieplanner-mobile/docs/google-play/last-version-code.txt — последний залитый/собранный code. Скрипт ставит max(файл, EAS remote) + 1. После каждой сборки AAB файл обновляется. Ошибка «код N уже использован» → записать N в файл, пересобрать.
Правило для агента: movieplanner-mobile/.cursor/rules/android-play-version-before-build.mdc.
Build order (RuStore AAB — отдельный артефакт)
Не путать с Play. RuStore = другой канал (APP_VARIANT=rustore), другой файл:
cd movieplanner-mobile
export ANDROID_HOME="$HOME/Library/Android/sdk"
export EXPO_TOKEN=$(grep '^EXPO_TOKEN=' ../movie_planner_bot/.env | cut -d= -f2-)
./scripts/build-rustore-aab.sh
Артефакт: MoviePlanner-RuStore-release.aab в корне репо. Скилл: movieplanner-mobile/.cursor/skills/local-rustore-aab-build/SKILL.md.
Если просят «aab и rustore aab» — собрать оба скрипта подряд и отдать оба пути.
Build order (ручные шаги)
- Check for an
android/ directory in movieplanner-mobile.
- If it is missing, generate it with Expo prebuild:
npx expo prebuild --platform android --non-interactive
After prebuild, re-run sync-android-upload-keystore.sh and re-apply release signing in android/app/build.gradle if prebuild reset it.
- Перед
bundleRelease: ./scripts/ensure-android-version-for-play.sh
- Build AAB locally:
cd android
./gradlew bundleRelease
cd ..
- Build APK locally when APK is requested:
cd android
./gradlew assembleRelease
cd ..
- Copy to root with fixed names and remove scattered copies:
./scripts/copy-release-artifacts.sh
Optional Gradle cleanup after copy: CLEAN_GRADLE=1 ./scripts/copy-release-artifacts.sh
Gradle writes to android/app/build/outputs/ — that is intermediate only; the user-facing file is MoviePlanner-release.aab / .apk in project root.
EAS local Android
./scripts/eas-build-android.sh --local
./scripts/copy-release-artifacts.sh
Important
- Do not ask the user to run the build manually.
- Do not use EAS as the only path if the account has hit Android build limits.
- If signing fails, run
./scripts/sync-android-upload-keystore.sh, then inspect android/gradle.properties, android/app/build.gradle, and movieplanner-mobile/.cursor/skills/android-play-signing/SKILL.md.
- Before telling the user the AAB is ready for Play, verify SHA1 matches
58:68:C5:8A:… (not debug 5E:8F:16:06:…).
- Do not commit generated
android/ changes unless the user asks; local build artifacts are enough unless source changes were needed.
- Before rebuilding, delete old root-level
*.aab / *.apk / build-* copies (not android/ source or node_modules).