Откройте Actions → Prepare and merge release → Run workflow, выберите main
и задайте новую версию, например 0.1.2 (без v). Запуск разрешает создание
релизного PR, автоматическое слияние с merge-коммитом после полного CI и создание тега.
Существующий Release Android artifacts затем соберёт, подпишет и опубликует APK.
Это не заменяет проверку релиза на устройствах.
Workflow уже находится в main. Добавление секретов не запускает выпуск;
workflow нужно явно запустить с новой версией.
В Settings → Secrets and variables → Actions добавьте:
| Тип | Имя | Значение |
|---|---|---|
| Secret | OPENAI_API_KEY |
Ключ OpenAI API, только для генерации EN/RU текстов GitHub и F-Droid. |
| Variable / Secret | OPENAI_RELEASE_MODEL |
Доступная вашему API-проекту модель с Responses API Structured Outputs, например gpt-6.1-sol. Если заданы оба варианта, Variables имеют приоритет над Secrets. Неявного выбора другой модели нет. |
| Secret | RELEASE_BOT_TOKEN |
Fine-grained PAT только для этого репозитория: Contents read/write, Pull requests read/write, Actions read. |
Workflow по тегу также требует VIRUSTOTAL_API_KEY. После подписи все пять публичных
релизных APK отправляются в VirusTotal; для universal используется загрузка больших
файлов. Общее ожидание ограничено 30 минутами, запросы идут с интервалом не менее
16 секунд с учётом квоты публичного API. Нет ключа, ошибка API, незавершённый анализ
или malicious/suspicious блокируют публикацию: сначала разберите результат.
Автоматического обхода обнаружений нет. Ноль обнаружений не гарантирует безопасность.
VIRUSTOTAL.md и VIRUSTOTAL.json прикладываются к релизу; ссылки по SHA-256 попадают
в описание релиза и Actions summary. Повтор заменяет только отмеченный блок VirusTotal,
сохраняя остальной текст. При ошибке завершённые частичные результаты остаются артефактом
Actions. PR CI не получает API-ключ и не загружает APK. Отправляются только APK,
никогда ключи подписи, профили или диагностические журналы.
API загрузки и ограничения размера,
статусы анализа и результаты.
Сохраните существующие секреты подписи для сборки по тегу:
ANDROID_SIGNING_KEY_BASE64, ANDROID_KEYSTORE_PASSWORD, ANDROID_KEY_ALIAS,
ANDROID_KEY_PASSWORD. Подготовка и проверки PR их не получают.
Разрешите merge-коммиты. Защитите main, сделайте обязательными Change scope,
Python tests and style, Native Go tests, Android tests and checks,
Android emulator API 26 / Device tests, Android emulator API 35 / Device tests
и отключите обход правил для бота. Если правила требуют человеческое ревью, одобрите созданный
PR самостоятельно: workflow не одобряет себя и не обходит запрет. После отказа
merge можно одобрить PR и перезапустить упавший finalize job. Merge queue этим
workflow с прямым merge не поддерживается. Правила тегов должны разрешать
боту создавать v*.
Отдельный аккаунт бота позволяет отделить его права от ваших. В первой реализации используется PAT; выпуск/продление GitHub App installation token не реализованы. Не сохраняйте короткоживущий installation token как постоянный секрет.
Отдельный токен нужен, поскольку, согласно GitHub, PR от GITHUB_TOKEN требуют
одобрения запуска workflow, а его push не запускает следующий workflow. PAT
позволяет автоматически запустить PR CI и сборку после создания тега.
Поведение GitHub token.
- Checkout выбранного commit
main. Остановка, еслиmainуже изменился, checkout грязный, версия некорректна либо ветка/тег уже существуют. - Выбор максимального стабильного опубликованного
vX.Y.Z, достижимого из этого commit, со всеми пятью загруженными непустыми APK иSHA256SUMS; черновики, prerelease, голые теги и неполные релизы пропускаются. В OpenAI передаются сообщения коммитов без merge и сам diff, кроме исторических changelog, сгенерированных release notes и lock/sum-файлов. Repository secrets и материалы подписи не читаются. До 600 000 символов входного текста обрабатываются одним запросом. Большой контекст делится на ограниченные части, по возможности по границам файлов: каждый исходный символ передаётся на подготовку фактической сводки. Если сводки тоже велики, они сокращаются следующими раундами перед генерацией итоговых заметок. Целевой размер сводки — 20 000 символов; более длинный непустой ответ сохраняется. Каждый раунд обязан уменьшать общий контекст. Автоматического усечения входа или замены модели нет. Для больших релизов требуется больше API-запросов; на подготовку отводится 30 минут. Запросы платные; unit-тесты подменяют API. - Генерация одинаковых по смыслу EN/RU списков: один пункт — одно предложение, до 10 пунктов и 3000 символов на язык для GitHub и отдельная выжимка до 500 символов на язык для F-Droid. Текст описывает конкретное поведение, объединяет связанные исправления и избегает общих обещаний; при изменениях только инфраструктуры кратко называет их и сообщает, что поведение приложения не изменилось. Отказ, некорректный ответ и ошибки API останавливают процесс до записи файлов. Фактическая модель, диапазон Git, расход токенов и длины сводок выводятся без ключей и сгенерированного текста, в том числе до ошибки валидации. Проверка JSON и промежуточные сводки не подтверждают полноту или достоверность — проверьте текст в PR.
- Создание
release/vX.Y.Z, обновлениеversionNameи увеличениеversionCodeBaseна единицу вapp/build.gradle.kts. Формулаbase * 1000 + ABI offsetсохраняется для F-Droid и обновлений того же варианта. Например base 14 → 15: universal15000, arm15001, arm6415002, x8615003, x86_6415004. - Добавление для этого примера
fastlane/metadata/android/{en-US,ru-RU}/changelogs/15000.txt–15004.txtи PR вmain. В каждом языке один текст сохраняется для universal и всех ABI APK, чтобы F-Droid находил его по коду версии APK. Отдельный двуязычный текст GitHub сохраняется вrelease-notes/X.Y.Z.md. Исторические changelog и описания карточки не переписываются. - Ожидание до 60 минут CI / pull_request именно для этого PR и head SHA.
Release-ветки запускают все наборы тестов уже с первой попытки. Все шесть
перечисленных выше обязательных job должны получить
success: skipped, neutral, failure и cancelled недостаточны. Записанная база сравнения должна совпасть с parent релизного commit. Номер PR также сохраняется успешным шагом CI: GitHub может убрать связь run с PR после merge, а этот шаг позволяет проверить повторное создание тега. - Повторная проверка PR и неизменности
main, merge с отдельным merge-коммитом и ожидаемым head SHA. Правила GitHub продолжают действовать. Проверка принадлежности итогового commit кmain, двух родителей (проверенные base и head) и точного совпадения его дерева с проверенным head. - Lightweight-тег
vX.Y.Zставится на фактический commit после merge, не на head ветки и не на более поздний случайныйmain. PAT запускает обычную сборку по тегу. Новый GitHub Release использует EN/RU текст изrelease-notes/X.Y.Z.md. Повтор finalize принимает уже существующий правильный тег, но никогда не переставляет тег, указывающий на другой commit.
Новая версия должна быть выше версии в коде и последнего стабильного тега.
Prerelease и автоматический выбор номера не поддерживаются. Подготовка и finalize
исполняют доверенные исходники workflow, а не код из релизного PR. Релизный commit
может менять только два поля версии Gradle, десять файлов changelog (пять кодов APK на язык)
и release-notes/X.Y.Z.md. Параллельные запуски
подготовки выполняются последовательно.
Повтор не делает force-push, не двигает теги и не переписывает историю. Упавшая проверка оставляет доступный PR без тега. После исправления/повтора CI выбирайте Re-run failed jobs у workflow подготовки, если head и base PR не изменились. Повтор использует результаты подготовки, не оплачивая ещё один ответ API. Если merge уже прошёл, а создание тега не удалось, повтор finalize заново проверит CI/дерево и создаст или проверит тег без повторного merge.
Если main или head изменились, старый finalize не должен одобрять новый код.
Осознанно обновите ветку так, чтобы единственный релизный commit был основан
на текущем main, дождитесь полного CI, затем завершите выпуск с явно выбранным
новым head из доверенного checkout main, с авторизованным gh и Fastlane:
export GITHUB_REPOSITORY=andre487/AndroidMegaProxy
bundle exec fastlane android release_finish version:0.1.2 pr:123 head:FULL_40_CHARACTER_SHAСкрипт fetch-ит PR для проверки, но не делает checkout и не исполняет его код. Команда выполняет merge и тег; это не dry run. Если ветка была отправлена, но создание PR не удалось, проверьте её, создайте PR вручную и используйте тот же способ восстановления. Новый запуск подготовки не подхватывает и не заменяет существующую ветку молча. При сбое сборки по тегу повторяйте эту сборку, не двигая тег. Внешняя заявка/recipe F-Droid автоматически не обновляются.
Ручная подготовка: bundle exec fastlane android release_prepare version:0.1.2
из чистого актуального checkout main, с теми же API/token/model настройками.
Формат API: OpenAI Structured Outputs. Условия merge: GitHub merge API.
Предпросмотр существующего релиза без записи релизных файлов и публикации:
bundle exec fastlane android release_notes_preview version:1.1.3 ref:v1.1.3Заранее задайте OPENAI_API_KEY и OPENAI_RELEASE_MODEL в окружении. Явный ref
исключает более поздние коммиты; тексты GitHub и F-Droid выводятся в терминал.
Для автоматического выбора базы нужны GITHUB_REPOSITORY=owner/repo и авторизованный gh.
Параметр previous:v1.1.1 позволяет явно переопределить базу.