From 035988e2ffce5955ffab96ae9d312fd9e86a193a Mon Sep 17 00:00:00 2001 From: tobiasKaminsky Date: Tue, 29 Sep 2026 08:49:18 +0200 Subject: [PATCH 1/2] extract Fastlane Signed-off-by: tobiasKaminsky --- .gitignore | 1 + Gemfile | 10 +- Gemfile.lock | 60 ++-- app/build.gradle.kts | 17 +- app/src/main/res/values/setup.xml | 2 +- fastlane/Fastfile | 557 +++++++++++------------------- 6 files changed, 236 insertions(+), 411 deletions(-) diff --git a/.gitignore b/.gitignore index 814761a6a1b6..053f1560db9b 100644 --- a/.gitignore +++ b/.gitignore @@ -60,6 +60,7 @@ build /gradle.properties .attach_pid* fastlane/Fastfile +fastlane/ruby *.hprof # NDK / C++ diff --git a/Gemfile b/Gemfile index b734015f8209..e8468385fbea 100644 --- a/Gemfile +++ b/Gemfile @@ -1,10 +1,4 @@ -# Autogenerated by fastlane -# -# Ensure this file is checked in to source control! - source "https://rubygems.org" -gem 'fastlane' - -plugins_path = File.join(File.dirname(__FILE__), 'fastlane', 'Pluginfile') -eval_gemfile(plugins_path) if File.exist?(plugins_path) +gem "fastlane" +gem "abbrev" diff --git a/Gemfile.lock b/Gemfile.lock index d4a325823d3b..0584204f5879 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -8,7 +8,7 @@ GEM artifactory (3.0.17) atomos (0.1.3) aws-eventstream (1.4.0) - aws-partitions (1.1287.0) + aws-partitions (1.1290.0) aws-sdk-core (3.257.0) aws-eventstream (~> 1, >= 1.3.0) aws-partitions (~> 1, >= 1.992.0) @@ -21,7 +21,7 @@ GEM aws-sdk-kms (1.132.0) aws-sdk-core (~> 3, >= 3.256.0) aws-sigv4 (~> 1.5) - aws-sdk-s3 (1.232.0) + aws-sdk-s3 (1.232.2) aws-sdk-core (~> 3, >= 3.256.0) aws-sdk-kms (~> 1) aws-sigv4 (~> 1.5) @@ -30,8 +30,8 @@ GEM babosa (1.0.4) base64 (0.3.0) benchmark (0.5.0) - bigdecimal (3.3.1) - cgi (0.4.2) + bigdecimal (4.1.3) + cgi (0.5.2) claide (1.1.0) colored (1.2) colored2 (3.1.2) @@ -41,11 +41,12 @@ GEM declarative (0.0.20) digest-crc (0.7.0) rake (>= 12.0.0, < 14.0.0) - domain_name (0.6.20260907) + domain_name (0.6.20260921) dotenv (2.8.1) emoji_regex (3.2.3) erb (6.0.7) - excon (0.112.0) + excon (1.7.1) + logger faraday (2.14.4) faraday-net_http (>= 2.0, < 3.5) json @@ -57,7 +58,8 @@ GEM faraday (>= 1, < 3) faraday-multipart (1.2.0) multipart-post (~> 2.0) - faraday-net_http (2.1.0) + faraday-net_http (3.4.4) + net-http (~> 0.5) faraday-retry (2.4.0) faraday (~> 2.0) fastimage (2.4.1) @@ -115,25 +117,24 @@ GEM xcodeproj (>= 1.13.0, < 2.0.0) xcpretty (~> 0.4.1) xcpretty-travis-formatter (>= 0.0.3, < 2.0.0) - fastlane-plugin-huawei_appgallery_connect (1.0.31) - cgi fastlane-sirp (1.1.0) gh_inspector (1.1.3) - google-apis-androidpublisher_v3 (0.108.0) + google-apis-androidpublisher_v3 (0.109.0) google-apis-core (>= 0.15.0, < 2.a) - google-apis-core (0.18.0) - addressable (~> 2.5, >= 2.5.1) - googleauth (~> 1.9) - httpclient (>= 2.8.3, < 3.a) - mini_mime (~> 1.0) - mutex_m + google-apis-core (1.2.5) + addressable (~> 2.9) + faraday (~> 2.13) + faraday-follow_redirects (~> 0.3) + googleauth (~> 1.14) + mini_mime (~> 1.1) + multi_json (~> 1.11) representable (~> 3.0) - retriable (>= 2.0, < 4.a) + retriable (>= 3.1, < 5.0) google-apis-iamcredentials_v1 (0.28.0) google-apis-core (>= 0.15.0, < 2.a) google-apis-playcustomapp_v1 (0.18.0) google-apis-core (>= 0.15.0, < 2.a) - google-apis-storage_v1 (0.67.0) + google-apis-storage_v1 (0.68.0) google-apis-core (>= 0.15.0, < 2.a) google-cloud-core (1.9.0) google-cloud-env (>= 1.0, < 3.a) @@ -163,9 +164,7 @@ GEM highline (2.0.3) http-cookie (1.1.6) domain_name (~> 0.5) - httpclient (2.9.0) - mutex_m - io-console (0.9.3) + io-console (0.9.4) irb (1.18.0) pp (>= 0.6.0) prism (>= 1.3.0) @@ -173,7 +172,7 @@ GEM reline (>= 0.4.2) jmespath (1.6.2) json (2.21.2) - jwt (2.10.3) + jwt (3.3.0) base64 logger (1.7.0) mini_magick (4.13.2) @@ -183,6 +182,8 @@ GEM mutex_m (0.3.0) nanaimo (0.4.0) naturally (2.3.0) + net-http (0.9.1) + uri (>= 0.11.1) nkf (0.3.0) optparse (0.8.1) os (1.1.4) @@ -193,7 +194,7 @@ GEM prettyprint (0.2.0) prism (1.9.0) pstore (0.2.1) - public_suffix (6.0.2) + public_suffix (7.0.5) rake (13.4.2) rbs (4.2.0) logger @@ -206,14 +207,14 @@ GEM tsort reline (0.7.0) io-console (~> 0.5) - representable (3.2.0) + representable (3.3.0) declarative (< 0.1.0) trailblazer-option (>= 0.1.1, < 0.2.0) uber (< 0.2.0) - retriable (3.8.0) + retriable (4.2.0) rexml (3.4.4) rouge (3.28.0) - rubyzip (3.6.0) + rubyzip (3.7.0) security (0.3.0) signet (0.22.0) addressable (~> 2.8) @@ -232,7 +233,10 @@ GEM tty-spinner (0.9.3) tty-cursor (~> 0.7) uber (0.1.0) - unicode-display_width (2.6.0) + unicode-display_width (3.3.0) + unicode-emoji (~> 4.3) + unicode-emoji (4.3.0) + uri (1.1.1) word_wrap (1.0.0) xcodeproj (1.28.1) CFPropertyList (>= 2.3.3, < 4.0) @@ -252,8 +256,8 @@ PLATFORMS x86_64-linux DEPENDENCIES + abbrev fastlane - fastlane-plugin-huawei_appgallery_connect BUNDLED WITH 2.5.4 diff --git a/app/build.gradle.kts b/app/build.gradle.kts index 9db2148e375c..5e2b0d112ca7 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -68,12 +68,6 @@ configurations.configureEach { } } -// semantic versioning for version code -val versionMajor = 35 -val versionMinor = 1 -val versionPatch = 0 -val versionBuild = 50 // 0-50=Alpha / 51-98=RC / 90-99=stable - val ndkEnv = buildMap { file("${project.rootDir}/ndk.env").readLines().forEach { val (key, value) = it.split("=") @@ -114,8 +108,10 @@ android { ) applicationId = "com.nextcloud.client" minSdk = 28 - targetSdk = 36 compileSdk = 37 + targetSdk = 36 + versionCode = 350010050 + versionName = "35.1.0 Alpha 51" ndk { abiFilters += listOf("armeabi-v7a", "arm64-v8a", "x86", "x86_64") @@ -128,13 +124,6 @@ android { testInstrumentationRunner = if (shotTest) "com.karumi.shot.ShotTestRunner" else "com.nextcloud.client.TestRunner" - versionCode = versionMajor * 10000000 + versionMinor * 10000 + versionPatch * 100 + versionBuild - versionName = when { - versionBuild > 89 -> "${versionMajor}.${versionMinor}.${versionPatch}" - versionBuild > 50 -> "${versionMajor}.${versionMinor}.${versionPatch} RC" + (versionBuild - 50) - else -> "${versionMajor}.${versionMinor}.${versionPatch} Alpha" + (versionBuild + 1) - } - // adapt structure from Eclipse to Gradle/Android Studio expectations; // see http://tools.android.com/tech-docs/new-build-system/user-guide#TOC-Configuring-the-Structure diff --git a/app/src/main/res/values/setup.xml b/app/src/main/res/values/setup.xml index 1c47e9f57d4f..a758c6884e77 100644 --- a/app/src/main/res/values/setup.xml +++ b/app/src/main/res/values/setup.xml @@ -90,7 +90,7 @@ https://nextcloud.com/privacy false true - false + true true https://github.com/nextcloud/android true diff --git a/fastlane/Fastfile b/fastlane/Fastfile index f72e30f3df0c..b1f4d9bdf1a8 100644 --- a/fastlane/Fastfile +++ b/fastlane/Fastfile @@ -1,24 +1,13 @@ # SPDX-FileCopyrightText: 2017-2024 Nextcloud GmbH and Nextcloud contributors # SPDX-License-Identifier: AGPL-3.0-or-later OR GPL-2.0-only -# run fastlane -# bundle exec fastlane - -# update fastlane -# bundle update fastlane - -# update plugins -# bundle exec fastlane update_plugins - -# This is the minimum version number required. -fastlane_version "2.58.0" ## config # add following to your shell rc: -# export FASTLANE_NEXTCLOUD_STORE_FILE="" -# export FASTLANE_NEXTCLOUD_STORE_PASSWORD="" -# export FASTLANE_NEXTCLOUD_KEY_ALIAS="" -# export FASTLANE_NEXTCLOUD_KEY_PASSWORD="" +# export FASTLANE_NEXTCLOUD_UPLOAD_STORE_FILE="" +# export FASTLANE_NEXTCLOUD_UPLOAD_STORE_PASSWORD="" +# export FASTLANE_NEXTCLOUD_UPLOAD_KEY_ALIAS="" +# export FASTLANE_NEXTCLOUD_UPLOAD_KEY_PASSWORD="" # export FASTLANE_NEXTCLOUD_GITHUB_API_TOKEN="" # export FASTLANE_NEXTCLOUD_HUAWEI_CLIENT_ID="" # export FASTLANE_NEXTCLOUD_HUAWEI_CLIENT_SECRET="" @@ -26,367 +15,215 @@ fastlane_version "2.58.0" skip_docs -## public lanes - -lane :screenshotsPhone do - beautifyPhone() - build_for_screengrab() - - screengrab( - device_type: "phone", - app_apk_path: APK_LOCATION, - tests_apk_path: TEST_APK_LOCATION - ) -end - -lane :screenshotsTablet do - beautifyPhone() - build_for_screengrab() - - screengrab( - device_type: "sevenInch", - app_apk_path: APK_LOCATION, - tests_apk_path: TEST_APK_LOCATION - ) -end - -desc "Release phase 1: make gplay/generic for RC, then test it" -lane :RC_releasePhase1 do - disableLogger() - makeReleases() - enableLogger() -end - -desc "Release phase 2 for RC: checks, tag, upload gplay to playstore with values from build.gradle.kts" -lane :RC_releasePhase2 do |options| - checkReleaseRequirements_RC() - info = androidVersion - promptVersion(info) - checkChangelog(info) - checkLibrary_RC() - checkIfScreenshotsExist() - checkIfAPKexists() - tag(info) - uploadToPlaystore_RC(info) - createGithubRelease_RC(info) - fdroidMergeRequest_RC(info) - createChangelogPullRequest_RC(info) -end - -desc "Release phase 1: make gplay/generic for FINAL, then test it" -lane :Final_releasePhase1 do - makeReleases() -end -desc "Release phase 2 for FINAL: checks, tag, upload gplay to playstore with values from build.gradle.kts" -lane :Final_releasePhase2 do |options| - checkReleaseRequirements_Final() - info = androidVersion - promptVersion(info) - checkChangelog(info) - checkLibrary_Final() - checkIfScreenshotsExist() - checkIfAPKexists() - tag(info) - uploadToPlaystore_Final(info) - createGithubRelease_Final(info) - fdroidMergeRequest_Final(info) - createChangelogPullRequest_Final(info) - uploadToHuawei_Final(info) -end +APP="files" +REPO="nextcloud/android" -desc "Makes gplay and generic releases in ../releases/" -lane :makeReleases do - info = androidVersion - sh("rm -rf ../release/ && mkdir -p ../release") - gradle(task: 'clean') +GRADLE_SIGNING_PROPERTIES = { + "android.injected.signing.store.file" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_STORE_FILE"], + "android.injected.signing.store.password" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_STORE_PASSWORD"], + "android.injected.signing.key.alias" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_KEY_ALIAS"], + "android.injected.signing.key.password" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_KEY_PASSWORD"], +}.freeze - createGenericRelease(versionCode:info["versionCode"]) +import("./common.Fastfile") - createGplayRelease(versionCode:info["versionCode"]) +platform :android do - createHuaweiRelease() -end - -desc "Create GPlay release" -lane :createGplayRelease do |options| - buildBundle(flavor:"Gplay") - sh("mv ../app/build/outputs/bundle/gplayRelease/app-gplay-release.aab ../release/") - buildApkFromBundle(outputDir: "../release", bundlePath: "../release/app-gplay-release.aab") - sh("rm ../release/toc.pb") - sh("mv ../release/universal.apk ../release/gplay-release-#{options[:versionCode]}.apk") -end - -desc "Create Generic release" -lane :createGenericRelease do |options| - SignedRelease(flavor:"Generic") - sh("mv ../app/build/outputs/apk/generic/release/*.apk ../release/") - sh("mv ../release/app-generic-release.apk ../release/nextcloud-#{options[:versionCode]}.apk") -end - -desc "Create Huawei release" -lane :createHuaweiRelease do - SignedRelease(flavor:"Huawei") - sh("mv ../app/build/outputs/apk/huawei/release/*.apk ../release/") -end - -desc "Create Dev release" -lane :createDevRelease do - SignedRelease(flavor:"VersionDev") - sh("mv ../app/build/outputs/apk/versionDev/release/*.apk ../release/") -end - -desc "Beautify phone for screenshots: set time, remove other icons, no charging" -lane :beautifyPhone do - sh("adb shell settings put global sysui_demo_allowed 1") - sh("adb shell am broadcast -a com.android.systemui.demo -e command clock -e hhmm 1200") - sh("adb shell am broadcast -a com.android.systemui.demo -e command network -e mobile show -e level 4 -e datatype false") - sh("adb shell am broadcast -a com.android.systemui.demo -e command notifications -e visible false") - sh("adb shell am broadcast -a com.android.systemui.demo -e command battery -e plugged false -e level 100") -end - -# to install -# bundle exec fastlane add_plugin huawei_appgallery_connect -# bundle install --path build/vendor/bundle -private_lane :uploadToHuawei_Final do |options| - huawei_appgallery_connect( - client_id: ENV["FASTLANE_NEXTCLOUD_HUAWEI_CLIENT_ID"], - client_secret: ENV["FASTLANE_NEXTCLOUD_HUAWEI_CLIENT_SECRET"], - app_id: ENV["FASTLANE_NEXTCLOUD_HUAWEI_APP_ID"], - apk_path: "release/huawei-release-" + options["versionCode"] + ".apk", - submit_for_review: true, - delay_before_submit_for_review: 30, - ) -end - -## private lanes - -desc "Build debug and test APK for screenshots" -private_lane :build_for_screengrab do - build_android_app( - task: 'assemble', - flavor: 'Generic', - build_type: 'Debug' - ) - APK_LOCATION = lane_context[SharedValues::GRADLE_ALL_APK_OUTPUT_PATHS].select{ |i| i[/00/] }[0] - - build_android_app( - task: 'assemble', - flavor: 'Generic', - build_type: 'DebugAndroidTest' - ) - TEST_APK_LOCATION = lane_context[SharedValues::GRADLE_ALL_APK_OUTPUT_PATHS].select{ |i| i[/androidTest/] }[0] -end - -private_lane :checkReleaseRequirements_common do - sh("if ! command -v fdroid &>/dev/null; then echo 'fdroid command not found' && exit 1; fi") - sh("if ! command -v bundletool &>/dev/null; then echo 'bundletool command not found' && exit 1; fi") -end - -private_lane :checkReleaseRequirements_RC do - checkReleaseRequirements_common() - sh("if ! command -v fdroidMergeRequestRC &>/dev/null; then echo 'fdroidMergeRequestRC command not found'; exit 1; fi") - sh("if ! command -v createChangelogPullRequestRC &>/dev/null; then echo 'createChangelogPullRequestRC command not found'; exit 1; fi") -end - -private_lane :checkReleaseRequirements_Final do - checkReleaseRequirements_common() - sh("if ! command -v fdroidMergeRequestFinal &>/dev/null; then echo 'fdroidMergeRequestFinal command not found'; exit 1; fi") - sh("if ! command -v createChangelogPullRequestFinal &>/dev/null; then echo 'createChangelogPullRequestFinal command not found'; exit 1; fi") -end - -private_lane :createChangelogPullRequest_RC do |options| - sh("createChangelogPullRequestRC " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"] + " \"" + options["branch"] + "\" ") -end - -private_lane :createChangelogPullRequest_Final do |options| - sh("createChangelogPullRequestFinal " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"] + " \"" + options["branch"] + "\" ") -end - -private_lane :checkIfAPKexists do |options| - sh("if [ $(/bin/ls -1 ../release | wc -l) -ne 4 ]; then echo 'Release artifacts not present or wrong number present; aborting!' ; exit 1 ; - fi") -end - -desc "compute version" -private_lane :androidVersion do - File.open("../app/build.gradle.kts","r") do |f| - text = f.read - - # everything between Document and Authors - major = text.match(/val versionMajor\s*=\s*([0-9]*)/) - minor = text.match(/val versionMinor\s*=\s*([0-9]*)/) - patch = text.match(/val versionPatch\s*=\s*([0-9]*)/) - build = text.match(/val versionBuild\s*=\s*([0-9]*)/) - - majorInt = major[1].to_i - minorInt = minor[1].to_i - patchInt = patch[1].to_i - buildInt = build[1].to_i - - versionCode = majorInt * 10000000 + minorInt * 10000 + patchInt * 100 + buildInt + desc "Release phase 2 for RC: checks, tag, upload gplay to playstore with values from build.gradle.kts" + lane :RC_releasePhase2 do |options| + checkReleaseRequirements_RC() + info = androidVersion + promptVersion(info) + checkChangelog(info) + checkLibrary_RC() + checkIfScreenshotsExist() + checkIfAPKexists() + tag(info) + uploadToPlaystore_RC(info) + createGithubRelease_RC(info) + fdroidMergeRequest_RC(info) + createChangelogPullRequest_RC(info) + end + + desc "Release phase 2 for FINAL: checks, tag, upload gplay to playstore with values from build.gradle.kts" + lane :Final_releasePhase2 do |options| + checkReleaseRequirements_Final() + info = androidVersion + promptVersion(info) + checkChangelog(info) + checkLibrary_Final() + checkIfScreenshotsExist() + checkIfAPKexists() + tag(info) + uploadToPlaystore_Final(info) + createGithubRelease_Final(info) + fdroidMergeRequest_Final(info) + createChangelogPullRequest_Final(info) + uploadToHuawei_Final(info) + end - if buildInt > 89 - name = major[1] + "." + minor[1] + "." + patch[1] - tag = "stable-" + major[1] + "." + minor[1] + "." + patch[1] - branch = "stable-" + major[1] + "." + minor[1] - elsif buildInt > 50 - name = major[1] + "." + minor[1] + "." + patch[1] + " RC" + (buildInt - 50).to_s - tag = "rc-" + major[1] + "." + minor[1] + "." + patch[1] + "-" + format('%02d', (buildInt - 50)) - branch = "stable-" + major[1] + "." + minor[1] - else - name = major[1] + "." + minor[1] + "." + patch[1] + " Alpha " + format('%02d', (buildInt + 1)) - tag = "/" - branch = "stable-" + major[1] + "." + minor[1] + # to install + # bundle exec fastlane add_plugin huawei_appgallery_connect + # bundle install --path build/vendor/bundle + private_lane :uploadToHuawei_Final do |options| + huawei_appgallery_connect( + client_id: ENV["FASTLANE_NEXTCLOUD_HUAWEI_CLIENT_ID"], + client_secret: ENV["FASTLANE_NEXTCLOUD_HUAWEI_CLIENT_SECRET"], + app_id: ENV["FASTLANE_NEXTCLOUD_HUAWEI_APP_ID"], + apk_path: "release/huawei-release-" + options["versionCode"] + ".apk", + submit_for_review: true, + delay_before_submit_for_review: 30, + ) + end + + ## private lanes + private_lane :checkReleaseRequirements_common do + sh("if ! command -v fdroid &>/dev/null; then echo 'fdroid command not found' && exit 1; fi") + sh("if ! command -v bundletool &>/dev/null; then echo 'bundletool command not found' && exit 1; fi") + end + + private_lane :checkReleaseRequirements_RC do + checkReleaseRequirements_common() + sh("if ! command -v fdroidMergeRequestRC &>/dev/null; then echo 'fdroidMergeRequestRC command not found'; exit 1; fi") + sh("if ! command -v createChangelogPullRequestRC &>/dev/null; then echo 'createChangelogPullRequestRC command not found'; exit 1; fi") + end + + private_lane :checkReleaseRequirements_Final do + checkReleaseRequirements_common() + sh("if ! command -v fdroidMergeRequestFinal &>/dev/null; then echo 'fdroidMergeRequestFinal command not found'; exit 1; fi") + sh("if ! command -v createChangelogPullRequestFinal &>/dev/null; then echo 'createChangelogPullRequestFinal command not found'; exit 1; fi") + end + + private_lane :createChangelogPullRequest_RC do |options| + sh("createChangelogPullRequestRC " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"] + " \"" + options["branch"] + "\" ") + end + + private_lane :createChangelogPullRequest_Final do |options| + sh("createChangelogPullRequestFinal " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"] + " \"" + options["branch"] + "\" ") + end + + private_lane :checkIfAPKexists do |options| + sh("if [ $(/bin/ls -1 ../release | wc -l) -ne 4 ]; then echo 'Release artifacts not present or wrong number present; aborting!' ; exit 1 ; + fi") + end + + desc "Show versions and prompt for confirmation" + private_lane :promptVersion do |options| + print "VersionCode: " + options["versionCode"].to_s + "\n" + print "Name: " + options["versionName"] + "\n" + print "Tag: " + options["tag"] + "\n" + print "Branch: " + options["branch"] + "\n" + + answer = prompt(text: "is this okay?", boolean: true) + + if !answer + exit end - - { "versionCode" => versionCode.to_s, "versionName" => name, "tag" => tag, "branch" => branch } end -end - -desc "Show versions and prompt for confirmation" -private_lane :promptVersion do |options| - print "VersionCode: " + options["versionCode"].to_s + "\n" - print "Name: " + options["versionName"] + "\n" - print "Tag: " + options["tag"] + "\n" - print "Branch: " + options["branch"] + "\n" - print "\ndisable IPv6 to upload to Gplay!!!\n" - - answer = prompt(text: "is this okay?", boolean: true) - - if !answer - exit + + desc "check if library is set correctly" + private_lane :checkLibrary_RC do + sh(" if [ $(egrep 'androidLibraryVersion.*master.*' ../build.gradle.kts -c) -eq 1 ] ; then echo 'Library is set to master tag; aborting!' ; exit 1 ; fi") + end + + desc "check if library is set correctly: must NOT contain master nor rc" + private_lane :checkLibrary_Final do + sh(" if [ $(grep 'androidLibraryVersion' ../build.gradle.kts | egrep 'master|rc' -c) -eq 1 ] ; then echo 'Library is still set to rc tag; aborting!' ; exit 1 ; fi") + end + + desc "check if screenshots exists and exit" + private_lane :checkIfScreenshotsExist do + sh(" if [ $(find metadata/android/*/images -type f -not -name icon.png | grep -c . ) -gt 0 ] ; then echo 'Screenshots in fastlane folder exist; aborting!' ; exit 1 ; fi") + end + + private_lane :createGithubRelease_RC do |options| + set_github_release( + repository_name: REPO, + api_token: ENV["FASTLANE_NEXTCLOUD_GITHUB_API_TOKEN"], + name: options["versionName"], + tag_name: options["tag"], + is_prerelease: true, + description: (File.read("metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt") rescue "No changelog provided"), + upload_assets: [ "release/gplay-release-" + options["versionCode"] + ".apk", "release/nextcloud-" + + options["versionCode"] + ".apk" ] + ) + end + + private_lane :createGithubRelease_Final do |options| + set_github_release( + repository_name: REPO, + api_token: ENV["FASTLANE_NEXTCLOUD_GITHUB_API_TOKEN"], + name: options["versionName"], + tag_name: options["tag"], + description: (File.read("metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt") rescue "No changelog provided"), + upload_assets: Dir.glob("release/*.apk") + ) + end + + private_lane :fdroidMergeRequest_RC do |options| + sh("fdroidMergeRequestRC " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"]) + end + + private_lane :fdroidMergeRequest_Final do |options| + sh("fdroidMergeRequestFinal " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"]) + end + + private_lane :checkChangelog do |options| + sh(" if [ ! -e metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt ] ; then echo 'Changelog fastlane/metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt does not exist' ; exit 1 ; fi") + sh(" if [ $(wc -m metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt | cut -d' ' -f1) -ge 500 ] ; then echo 'Changlog more than 500 chars' ; exit 1 ; fi") end -end - -desc "check if library is set correctly" -private_lane :checkLibrary_RC do - sh(" if [ $(egrep 'androidLibraryVersion.*master.*' ../build.gradle.kts -c) -eq 1 ] ; then echo 'Library is set to master tag; aborting!' ; exit 1 ; fi") -end - -desc "check if library is set correctly: must NOT contain master nor rc" -private_lane :checkLibrary_Final do - sh(" if [ $(grep 'androidLibraryVersion' ../build.gradle.kts | egrep 'master|rc' -c) -eq 1 ] ; then echo 'Library is still set to rc tag; aborting!' ; exit 1 ; fi") -end - -desc "check if screenshots exists and exit" -private_lane :checkIfScreenshotsExist do - sh(" if [ $(find metadata/android/*/images -type f -not -name icon.png | grep -c . ) -gt 0 ] ; then echo 'Screenshots in fastlane folder exist; aborting!' ; exit 1 ; fi") -end - -private_lane :tag do |options| - add_git_tag( - tag: options["tag"], - sign: true - ) - push_git_tags( - tag: options["tag"]) -end - -private_lane :disableLogger do - sh("sed -i s'#false#true#' ../app/src/main/res/values/setup.xml") -end - -private_lane :enableLogger do - sh("sed -i s'#true#false#' ../app/src/main/res/values/setup.xml") -end -desc "Upload to play store (beta)" -private_lane :uploadToPlaystore_RC do |options| - upload_to_play_store( - skip_upload_images: true, - track: 'beta', - aab: "release/app-gplay-release.aab" - ) -end -desc "Upload to play store" -private_lane :uploadToPlaystore_Final do |options| - upload_to_play_store( - skip_upload_images: true, - skip_upload_apk: true, - aab: "release/app-gplay-release.aab" - ) -end -desc "Build app bundle" -private_lane :buildBundle do |options| - gradle( - task: 'bundle', - flavor: options[:flavor], - build_type: 'Release', - print_command: false, - properties: { - "android.injected.signing.store.file" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_STORE_FILE"], - "android.injected.signing.store.password" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_STORE_PASSWORD"], - "android.injected.signing.key.alias" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_KEY_ALIAS"], - "android.injected.signing.key.password" => ENV["FASTLANE_NEXTCLOUD_UPLOAD_KEY_PASSWORD"], - } + ## to discuss if still needed + lane :screenshotsPhone do + beautifyPhone() + build_for_screengrab() + + screengrab( + device_type: "phone", + app_apk_path: APK_LOCATION, + tests_apk_path: TEST_APK_LOCATION ) -end - -desc "Generate signed universal APK from app bundle" -private_lane :buildApkFromBundle do |options| - sh(command:"bundletool build-apks --mode universal --output '#{options[:outputDir]}' --output-format DIRECTORY" + - " --ks '#{ENV["FASTLANE_NEXTCLOUD_STORE_FILE"]}'"+ - " --ks-pass 'pass:#{ENV["FASTLANE_NEXTCLOUD_STORE_PASSWORD"]}'"+ - " --ks-key-alias '#{ENV["FASTLANE_NEXTCLOUD_KEY_ALIAS"]}'"+ - " --key-pass 'pass:#{ENV["FASTLANE_NEXTCLOUD_KEY_PASSWORD"]}'"+ - " --bundle '#{options[:bundlePath]}'", - log:false) -end - -desc "Build signed APK" -private_lane :SignedRelease do |options| - gradle( - task: 'assemble', - flavor: options[:flavor], - build_type: 'Release', - print_command: false, - properties: { - "android.injected.signing.store.file" => ENV["FASTLANE_NEXTCLOUD_STORE_FILE"], - "android.injected.signing.store.password" => ENV["FASTLANE_NEXTCLOUD_STORE_PASSWORD"], - "android.injected.signing.key.alias" => ENV["FASTLANE_NEXTCLOUD_KEY_ALIAS"], - "android.injected.signing.key.password" => ENV["FASTLANE_NEXTCLOUD_KEY_PASSWORD"], - } + end + + lane :screenshotsTablet do + beautifyPhone() + build_for_screengrab() + + screengrab( + device_type: "sevenInch", + app_apk_path: APK_LOCATION, + tests_apk_path: TEST_APK_LOCATION ) -end - -private_lane :createGithubRelease_RC do |options| - set_github_release( - repository_name: "nextcloud/android", - api_token: ENV["FASTLANE_NEXTCLOUD_GITHUB_API_TOKEN"], - name: options["versionName"], - tag_name: options["tag"], - is_prerelease: true, - description: (File.read("metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt") rescue "No changelog provided"), - upload_assets: [ "release/gplay-release-" + options["versionCode"] + ".apk", "release/nextcloud-" + - options["versionCode"] + ".apk" ] - ) -end - -private_lane :createGithubRelease_Final do |options| - set_github_release( - repository_name: "nextcloud/android", - api_token: ENV["FASTLANE_NEXTCLOUD_GITHUB_API_TOKEN"], - name: options["versionName"], - tag_name: options["tag"], - description: (File.read("metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt") rescue "No changelog provided"), - upload_assets: [ "release/gplay-release-" + options["versionCode"] + ".apk", "release/nextcloud-" + - options["versionCode"] + ".apk" ] - ) -end + end -private_lane :fdroidMergeRequest_RC do |options| - sh("fdroidMergeRequestRC " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"]) -end + desc "Beautify phone for screenshots: set time, remove other icons, no charging" + lane :beautifyPhone do + sh("adb shell settings put global sysui_demo_allowed 1") + sh("adb shell am broadcast -a com.android.systemui.demo -e command clock -e hhmm 1200") + sh("adb shell am broadcast -a com.android.systemui.demo -e command network -e mobile show -e level 4 -e datatype false") + sh("adb shell am broadcast -a com.android.systemui.demo -e command notifications -e visible false") + sh("adb shell am broadcast -a com.android.systemui.demo -e command battery -e plugged false -e level 100") + end -private_lane :fdroidMergeRequest_Final do |options| - sh("fdroidMergeRequestFinal " + options["tag"] + " \"" + options["versionName"] + "\" " + options["versionCode"]) -end + desc "Build debug and test APK for screenshots" + private_lane :build_for_screengrab do + build_android_app( + task: 'assemble', + flavor: 'Generic', + build_type: 'Debug' + ) + APK_LOCATION = lane_context[SharedValues::GRADLE_ALL_APK_OUTPUT_PATHS].select{ |i| i[/00/] }[0] + + build_android_app( + task: 'assemble', + flavor: 'Generic', + build_type: 'DebugAndroidTest' + ) + TEST_APK_LOCATION = lane_context[SharedValues::GRADLE_ALL_APK_OUTPUT_PATHS].select{ |i| i[/androidTest/] }[0] + end -private_lane :checkChangelog do |options| - sh(" if [ ! -e metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt ] ; then echo 'Changelog fastlane/metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt does not exist' ; exit 1 ; fi") - sh(" if [ $(wc -m metadata/android/en-US/changelogs/" + options["versionCode"] + ".txt | cut -d' ' -f1) -ge 500 ] ; then echo 'Changlog more than 500 chars' ; exit 1 ; fi") end From 9d776fb603f617a25b11b8722a40bdad5610b065 Mon Sep 17 00:00:00 2001 From: tobiasKaminsky Date: Thu, 1 Oct 2026 08:04:23 +0200 Subject: [PATCH 2/2] clarify semVer Signed-off-by: tobiasKaminsky --- app/build.gradle.kts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/app/build.gradle.kts b/app/build.gradle.kts index 5e2b0d112ca7..ceef6d63019a 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -110,6 +110,8 @@ android { minSdk = 28 compileSdk = 37 targetSdk = 36 + // mayor.minor.hotfix.increment (for increment: 01-50=Alpha / 51-89=RC / 90-99=stable) + // xx .xxx .xx .xx versionCode = 350010050 versionName = "35.1.0 Alpha 51"