From a8b8f7746a43114e7a4eaabc72c79611efde7376 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 10:26:43 +0200 Subject: [PATCH 01/63] feat(qa-build): update pipeline for generating ios and android builds --- .github/workflows/test-ios-build-app.yml | 82 ++++++++++++++++++++++++ scripts/setup.mjs | 17 ++++- 2 files changed, 96 insertions(+), 3 deletions(-) create mode 100644 .github/workflows/test-ios-build-app.yml diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml new file mode 100644 index 00000000000..43bf06aae86 --- /dev/null +++ b/.github/workflows/test-ios-build-app.yml @@ -0,0 +1,82 @@ +name : Test iOS Build App + +on: + push: + + +jobs: + ios-e2e: + runs-on: macos-15 + env: + GITHUB_CI: "true" # โœ… This ensures it's available during pod install + steps: + - name: Checkout repo + uses: actions/checkout@v4 + + - name: Detect CPU architecture + run: | + echo "Arch: $(uname -m)" + if [[ "$(uname -m)" == "x86_64" ]]; then + echo "Detected Intel runner" + else + echo "Detected Apple Silicon runner" + fi + - name: Print system resources + run: | + echo "๐Ÿง  Memory info:" + vm_stat + echo "" + echo "๐Ÿ’ป CPU info:" + sysctl -n hw.ncpu + sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' + shell: bash + + + - name: Setup E2E iOS Environment + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + with: + platform: ios + setup-simulator: false + + - name: Print iOS tool versions + run: | + echo "๐Ÿ”ง Node.js Version:" + node -v || echo "Node not found" + echo "๐Ÿงถ Yarn Version:" + yarn -v || echo "Yarn not found" + echo "๐Ÿ“ฆ CocoaPods Version:" + pod --version || echo "CocoaPods not found" + echo "๐Ÿ› ๏ธ Xcode Path:" + xcode-select -p || echo "Xcode not found" + echo "๐Ÿ“ฑ Booted iOS Simulators:" + xcrun simctl list | grep Booted || echo "No booted simulators found" + shell: bash + + - name: Build iOS App + run: | + yarn setup --build-on-github-ci --build-ios --no-build-android + shell: bash + env: + PLATFORM: ios + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" + + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} diff --git a/scripts/setup.mjs b/scripts/setup.mjs index b3fa34ff238..6f687ca35e4 100644 --- a/scripts/setup.mjs +++ b/scripts/setup.mjs @@ -11,6 +11,8 @@ let BUILD_IOS = IS_OSX; let IS_NODE = false; let BUILD_ANDROID = true let INSTALL_PODS; +// GitHub CI pipeline flag - defaults to false +let GITHUB_CI = false; const args = process.argv.slice(2) || []; for (const arg of args) { switch (arg) { @@ -32,6 +34,9 @@ for (const arg of args) { case '--no-build-android': BUILD_ANDROID = false continue; + case '--build-on-github-ci': + GITHUB_CI = true; + continue; default: throw new Error(`Unrecognized CLI arg ${arg}`); } @@ -163,13 +168,19 @@ const setupIosTask = { const tasks = [ { title: 'Install bundler gem', - task: async () => { + task: async (_, task) => { + if (GITHUB_CI) { + return task.skip('Skipping bundler gem installation in GitHub CI.'); + } await $`gem install bundler -v 2.5.8`; }, }, { title: 'Install gems', - task: async () => { + task: async (_, task) => { + if (GITHUB_CI) { + return task.skip('Skipping gems installation in GitHub CI.'); + } await $`yarn gem:bundle:install`; }, }, @@ -182,7 +193,7 @@ const setupIosTask = { }, ]; - if (INSTALL_PODS) { + if (INSTALL_PODS && !GITHUB_CI) { tasks.push({ title: 'Install CocoaPods', task: async () => { From dd0c3cb87782388a7294876ece1500c5bd7a94ef Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 10:45:14 +0200 Subject: [PATCH 02/63] chore: update token --- .github/workflows/test-ios-build-app.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 43bf06aae86..2741c79edca 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -3,6 +3,9 @@ name : Test iOS Build App on: push: +permissions: + contents: write + id-token: write jobs: ios-e2e: From 8bf6ad253a106dfeb1984b9676e5ac2409631026 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 11:19:09 +0200 Subject: [PATCH 03/63] chore: test build now --- .github/workflows/test-ios-build-app.yml | 18 ++++++++++++++++-- scripts/setup.mjs | 10 ++++++++-- 2 files changed, 24 insertions(+), 4 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 2741c79edca..1047e42683f 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -8,7 +8,8 @@ permissions: id-token: write jobs: - ios-e2e: + ios-build: + name: Test iOS QA Build App runs-on: macos-15 env: GITHUB_CI: "true" # โœ… This ensures it's available during pod install @@ -55,7 +56,7 @@ jobs: xcrun simctl list | grep Booted || echo "No booted simulators found" shell: bash - - name: Build iOS App + - name: Setup iOS Environment run: | yarn setup --build-on-github-ci --build-ios --no-build-android shell: bash @@ -83,3 +84,16 @@ jobs: MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + + - name: Build iOS App + run: | + yarn build:ios:qa + shell: bash + env: + PLATFORM: ios + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" diff --git a/scripts/setup.mjs b/scripts/setup.mjs index 6f687ca35e4..0b4c69f6cb4 100644 --- a/scripts/setup.mjs +++ b/scripts/setup.mjs @@ -126,13 +126,19 @@ const buildPpomTask = { [ { title: 'Clean', - task: async () => { + task: async (_, task) => { + if (GITHUB_CI) { + return task.skip('Skipping clean in GitHub CI.'); + } await $ppom`yarn clean`; }, }, { title: 'Install deps', - task: async () => { + task: async (_, task) => { + if (GITHUB_CI) { + return task.skip('Skipping deps installation in GitHub CI.'); + } await $ppom`yarn`; }, }, From d41938583642aaec3641a3f27f0a52d442096b52 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 11:41:59 +0200 Subject: [PATCH 04/63] chore: test without prev steps --- .github/workflows/test-ios-build-app.yml | 10 +++++----- scripts/setup.mjs | 4 ++-- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 1047e42683f..a7f2ce96a9d 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -36,11 +36,11 @@ jobs: shell: bash - - name: Setup E2E iOS Environment - uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - with: - platform: ios - setup-simulator: false + # - name: Setup E2E iOS Environment + # uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + # with: + # platform: ios + # setup-simulator: false - name: Print iOS tool versions run: | diff --git a/scripts/setup.mjs b/scripts/setup.mjs index 0b4c69f6cb4..ed65d3306db 100644 --- a/scripts/setup.mjs +++ b/scripts/setup.mjs @@ -127,7 +127,7 @@ const buildPpomTask = { { title: 'Clean', task: async (_, task) => { - if (GITHUB_CI) { + if (!GITHUB_CI) { return task.skip('Skipping clean in GitHub CI.'); } await $ppom`yarn clean`; @@ -136,7 +136,7 @@ const buildPpomTask = { { title: 'Install deps', task: async (_, task) => { - if (GITHUB_CI) { + if (!GITHUB_CI) { return task.skip('Skipping deps installation in GitHub CI.'); } await $ppom`yarn`; From 252d39aa59afae7a31bdf4d1304b09acbc9b5442 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 12:11:09 +0200 Subject: [PATCH 05/63] chore: add setup:github-ci command --- .github/workflows/test-ios-build-app.yml | 12 ++++++------ package.json | 1 + scripts/setup.mjs | 7 ++----- 3 files changed, 9 insertions(+), 11 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index a7f2ce96a9d..626e265df4b 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -36,11 +36,11 @@ jobs: shell: bash - # - name: Setup E2E iOS Environment - # uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - # with: - # platform: ios - # setup-simulator: false + - name: Setup E2E iOS Environment + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + with: + platform: ios + setup-simulator: false - name: Print iOS tool versions run: | @@ -58,7 +58,7 @@ jobs: - name: Setup iOS Environment run: | - yarn setup --build-on-github-ci --build-ios --no-build-android + yarn setup:github-ci --build-ios --no-build-android shell: bash env: PLATFORM: ios diff --git a/package.json b/package.json index 5b4dcc09c1a..df6dcfb052f 100644 --- a/package.json +++ b/package.json @@ -22,6 +22,7 @@ "format": "prettier '**/*.{js,ts,tsx,json,feature}' --write", "format:check:changed": "git diff --name-only --diff-filter=ACM HEAD~1 | { grep -E '\\.(js|ts|tsx|json|feature)$' || true; } | xargs --no-run-if-empty prettier --check", "setup": "yarn clean && node scripts/setup.mjs", + "setup:github-ci": "node scripts/setup.mjs --build-on-github-ci", "setup:flask": "export METAMASK_BUILD_TYPE='flask' && yarn setup", "setup:expo": "yarn clean && node scripts/setup.mjs --no-build-ios --no-build-android", "setup:e2e": "cd wdio && yarn install", diff --git a/scripts/setup.mjs b/scripts/setup.mjs index ed65d3306db..d394254b68d 100644 --- a/scripts/setup.mjs +++ b/scripts/setup.mjs @@ -127,7 +127,7 @@ const buildPpomTask = { { title: 'Clean', task: async (_, task) => { - if (!GITHUB_CI) { + if (GITHUB_CI) { return task.skip('Skipping clean in GitHub CI.'); } await $ppom`yarn clean`; @@ -135,10 +135,7 @@ const buildPpomTask = { }, { title: 'Install deps', - task: async (_, task) => { - if (!GITHUB_CI) { - return task.skip('Skipping deps installation in GitHub CI.'); - } + task: async () => { await $ppom`yarn`; }, }, From fcab962b85366180124b40c82cc263dd1d057418 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 12:29:31 +0200 Subject: [PATCH 06/63] chore: introduce command within the same step --- .github/workflows/test-ios-build-app.yml | 14 +------------- 1 file changed, 1 insertion(+), 13 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 626e265df4b..a78ad2a4d0d 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -59,6 +59,7 @@ jobs: - name: Setup iOS Environment run: | yarn setup:github-ci --build-ios --no-build-android + yarn build:ios:qa shell: bash env: PLATFORM: ios @@ -84,16 +85,3 @@ jobs: MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} - - - name: Build iOS App - run: | - yarn build:ios:qa - shell: bash - env: - PLATFORM: ios - METAMASK_ENVIRONMENT: qa - METAMASK_BUILD_TYPE: main - IS_TEST: true - IGNORE_BOXLOGS_DEVELOPMENT: true - GITHUB_CI: "true" - CI: "true" From 681540c3c6917bfd6331cc436c727b7d74b31e30 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 13:49:35 +0200 Subject: [PATCH 07/63] chore: run android pipeline --- .github/workflows/test-android-build-app.yml | 91 ++++++++++++++++++++ .github/workflows/test-ios-build-app.yml | 87 ------------------- 2 files changed, 91 insertions(+), 87 deletions(-) create mode 100644 .github/workflows/test-android-build-app.yml delete mode 100644 .github/workflows/test-ios-build-app.yml diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml new file mode 100644 index 00000000000..27617b217f6 --- /dev/null +++ b/.github/workflows/test-android-build-app.yml @@ -0,0 +1,91 @@ +name: Test Android E2E Setup + +on: + push: + + +permissions: + contents: write + id-token: write + +jobs: + android-e2e: + runs-on: ubuntu-latest + steps: + - name: Checkout repo + uses: actions/checkout@v4 + + + - name: Setup E2E Android Environment + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + with: + platform: android + setup-simulator: false + + + - name: Print Android Environment Info + run: | + echo "๐Ÿ”ง Node.js Version:" + node -v || echo "Node not found" + echo "Android Studio Version:" + /Applications/Android\ Studio.app/Contents/MacOS/studio --version || echo "Check manually via finder" + echo "๐Ÿงถ Yarn Version:" + yarn -v || echo "Yarn not found" + echo "๐Ÿ“ฆ SDK Manager Version:" + sdkmanager --version || echo "sdkmanager not found" + echo "๐Ÿ“ฑ ADB Version:" + adb version || echo "adb not found" + echo "๐Ÿ–ฅ๏ธ Emulator Version:" + emulator -version || echo "emulator not found" + echo "๐Ÿงฑ NDK Info:" + echo "NDK Dir: $ANDROID_SDK_ROOT/ndk/${NDK_VERSION:-unknown}" + if [ -n "${NDK_VERSION}" ] && [ -f "$ANDROID_SDK_ROOT/ndk/${NDK_VERSION}/source.properties" ]; then + grep "Pkg.Revision" "$ANDROID_SDK_ROOT/ndk/${NDK_VERSION}/source.properties" || echo "NDK version info not found" + else + echo "NDK not found or NDK_VERSION not set" + fi + echo "๐Ÿ”ง Checking for ndk-build:" + command -v ndk-build || echo "ndk-build not found in PATH" + echo "๐Ÿ”ง Checking for clang:" + command -v clang || echo "clang not found in PATH" + echo "๐Ÿ”ง Checking for llvm-ar:" + command -v llvm-ar || echo "llvm-ar not found in PATH" + echo "๐Ÿ“ฑ Available AVD Devices:" + avdmanager list device || echo "avdmanager not found" + echo "๐Ÿ“ฑ Available System Images:" + sdkmanager --list | grep "system-images;" || echo "No system images listed" + echo "๐ŸŸข Emulator Processes:" + pgrep -fl emulator || echo "No running emulator processes" + echo "๐Ÿ“ฑ Connected Android Devices:" + adb devices || echo "adb devices failed" + shell: bash + + - name: Build iOS App + run: | + yarn setup:github-ci --build-on-github-ci --build-android --no-build-ios + yarn build:android:qa + shell: bash + env: + PLATFORM: android + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" + + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml deleted file mode 100644 index a78ad2a4d0d..00000000000 --- a/.github/workflows/test-ios-build-app.yml +++ /dev/null @@ -1,87 +0,0 @@ -name : Test iOS Build App - -on: - push: - -permissions: - contents: write - id-token: write - -jobs: - ios-build: - name: Test iOS QA Build App - runs-on: macos-15 - env: - GITHUB_CI: "true" # โœ… This ensures it's available during pod install - steps: - - name: Checkout repo - uses: actions/checkout@v4 - - - name: Detect CPU architecture - run: | - echo "Arch: $(uname -m)" - if [[ "$(uname -m)" == "x86_64" ]]; then - echo "Detected Intel runner" - else - echo "Detected Apple Silicon runner" - fi - - name: Print system resources - run: | - echo "๐Ÿง  Memory info:" - vm_stat - echo "" - echo "๐Ÿ’ป CPU info:" - sysctl -n hw.ncpu - sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' - shell: bash - - - - name: Setup E2E iOS Environment - uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - with: - platform: ios - setup-simulator: false - - - name: Print iOS tool versions - run: | - echo "๐Ÿ”ง Node.js Version:" - node -v || echo "Node not found" - echo "๐Ÿงถ Yarn Version:" - yarn -v || echo "Yarn not found" - echo "๐Ÿ“ฆ CocoaPods Version:" - pod --version || echo "CocoaPods not found" - echo "๐Ÿ› ๏ธ Xcode Path:" - xcode-select -p || echo "Xcode not found" - echo "๐Ÿ“ฑ Booted iOS Simulators:" - xcrun simctl list | grep Booted || echo "No booted simulators found" - shell: bash - - - name: Setup iOS Environment - run: | - yarn setup:github-ci --build-ios --no-build-android - yarn build:ios:qa - shell: bash - env: - PLATFORM: ios - METAMASK_ENVIRONMENT: qa - METAMASK_BUILD_TYPE: main - IS_TEST: true - IGNORE_BOXLOGS_DEVELOPMENT: true - GITHUB_CI: "true" - CI: "true" - - SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} - SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} - SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} - SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} - - MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} - MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} - - MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} - MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} - MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} - GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} - GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} From a0f3b8c15286eddb39b63f5557794f6b8912e61f Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 14:01:59 +0200 Subject: [PATCH 08/63] chore: remove repeated input --- .github/workflows/test-android-build-app.yml | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 27617b217f6..ef372a880f4 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -1,4 +1,4 @@ -name: Test Android E2E Setup +name: Test Android Build QA App on: push: @@ -9,7 +9,7 @@ permissions: id-token: write jobs: - android-e2e: + android-build: runs-on: ubuntu-latest steps: - name: Checkout repo @@ -60,9 +60,9 @@ jobs: adb devices || echo "adb devices failed" shell: bash - - name: Build iOS App + - name: Build Android App run: | - yarn setup:github-ci --build-on-github-ci --build-android --no-build-ios + yarn setup:github-ci --build-android --no-build-ios yarn build:android:qa shell: bash env: From 59042d0ca893fb545eb038c64b253f6a5ee0ef3c Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Fri, 25 Jul 2025 14:13:00 +0200 Subject: [PATCH 09/63] chore: remove input --- .github/workflows/test-android-build-app.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index ef372a880f4..af90c84e326 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -62,7 +62,7 @@ jobs: - name: Build Android App run: | - yarn setup:github-ci --build-android --no-build-ios + yarn setup:github-ci --no-build-ios yarn build:android:qa shell: bash env: From 274f3ab9e2d7331ca777df25c56a3ffe27eccaea Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Mon, 28 Jul 2025 11:42:22 +0200 Subject: [PATCH 10/63] chore: re enabled ios and launch both To test to upload the artifact to the registry --- .github/workflows/test-android-build-app.yml | 51 +++++++ .github/workflows/test-ios-build-app.yml | 150 +++++++++++++++++++ 2 files changed, 201 insertions(+) create mode 100644 .github/workflows/test-ios-build-app.yml diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index af90c84e326..7badbf23067 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -11,6 +11,11 @@ permissions: jobs: android-build: runs-on: ubuntu-latest + outputs: + artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} + apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} + aab-uploaded: ${{ steps.upload-aab.outcome == 'success' }} + sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} steps: - name: Checkout repo uses: actions/checkout@v4 @@ -62,6 +67,7 @@ jobs: - name: Build Android App run: | + echo "๐Ÿš€ Building Android APP..." yarn setup:github-ci --no-build-ios yarn build:android:qa shell: bash @@ -89,3 +95,48 @@ jobs: MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + + - name: Upload Android APK Artifact + id: upload-apk + uses: actions/upload-artifact@v4 + with: + name: android-app-qa + path: android/app/build/outputs/apk/qa/release/app-qa-release.apk + retention-days: 7 + if-no-files-found: error + continue-on-error: true + + - name: Upload Android AAB Artifact + id: upload-aab + uses: actions/upload-artifact@v4 + with: + name: android-bundle-qa + path: android/app/build/outputs/bundle/qaRelease/app-qa-release.aab + retention-days: 7 + if-no-files-found: warn + continue-on-error: true + + - name: Upload Android Source Map + id: upload-sourcemap + uses: actions/upload-artifact@v4 + with: + name: android-sourcemap-qa + path: sourcemaps/android/index.android.bundle.map + retention-days: 7 + if-no-files-found: warn + continue-on-error: true + + - name: Set Artifacts URL and Status + id: set-artifacts-url + run: | + ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" + echo "artifacts-url=${ARTIFACTS_URL}" >> $GITHUB_OUTPUT + echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" + echo "" + echo "Upload Status Summary:" + echo "- APK: ${{ steps.upload-apk.outcome }}" + echo "- AAB Bundle: ${{ steps.upload-aab.outcome }}" + echo "- Source Map: ${{ steps.upload-sourcemap.outcome }}" + env: + GITHUB_REPOSITORY: ${{ github.repository }} + GITHUB_RUN_ID: ${{ github.run_id }} diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml new file mode 100644 index 00000000000..14d48fab312 --- /dev/null +++ b/.github/workflows/test-ios-build-app.yml @@ -0,0 +1,150 @@ +name: Test iOS Build QA App + +on: + push: + +permissions: + contents: write + id-token: write + +jobs: + ios-build: + name: Test iOS QA Build App + runs-on: macos-15 + outputs: + artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} + ipa-uploaded: ${{ steps.upload-ipa.outcome == 'success' }} + archive-uploaded: ${{ steps.upload-archive.outcome == 'success' }} + sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} + env: + GITHUB_CI: "true" # โœ… This ensures it's available during pod install + steps: + - name: Checkout repo + uses: actions/checkout@v4 + + - name: Detect CPU architecture + run: | + echo "Arch: $(uname -m)" + if [[ "$(uname -m)" == "x86_64" ]]; then + echo "Detected Intel runner" + else + echo "Detected Apple Silicon runner" + fi + + - name: Print system resources + run: | + echo "๐Ÿง  Memory info:" + vm_stat + echo "" + echo "๐Ÿ’ป CPU info:" + sysctl -n hw.ncpu + sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' + shell: bash + + - name: Setup E2E iOS Environment + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + with: + platform: ios + setup-simulator: false + + - name: Print iOS tool versions + run: | + echo "๐Ÿ”ง Node.js Version:" + node -v || echo "Node not found" + echo "๐Ÿงถ Yarn Version:" + yarn -v || echo "Yarn not found" + echo "๐Ÿ“ฆ CocoaPods Version:" + pod --version || echo "CocoaPods not found" + echo "๐Ÿ› ๏ธ Xcode Path:" + xcode-select -p || echo "Xcode not found" + echo "๐Ÿ“ฑ Booted iOS Simulators:" + xcrun simctl list | grep Booted || echo "No booted simulators found" + shell: bash + + - name: Setup iOS Environment + run: | + yarn setup --build-on-github-ci --build-ios --no-build-android + shell: bash + env: + PLATFORM: ios + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" + + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + + - name: Build iOS App + run: | + echo "๐Ÿš€ Building iOS APP..." + yarn build:ios:qa + shell: bash + env: + PLATFORM: ios + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" + + - name: Upload iOS IPA Artifact + id: upload-ipa + uses: actions/upload-artifact@v4 + with: + name: ios-app-qa + path: ios/build/output/MetaMask-QA.ipa + retention-days: 7 + if-no-files-found: error + continue-on-error: true + + - name: Upload iOS Archive Artifact + id: upload-archive + uses: actions/upload-artifact@v4 + with: + name: ios-archive-qa + path: ios/build/MetaMask-QA.xcarchive + retention-days: 7 + if-no-files-found: warn + continue-on-error: true + + - name: Upload iOS Source Map + id: upload-sourcemap + uses: actions/upload-artifact@v4 + with: + name: ios-sourcemap-qa + path: sourcemaps/ios/index.js.map + retention-days: 7 + if-no-files-found: warn + continue-on-error: true + + - name: Set Artifacts URL and Status + id: set-artifacts-url + run: | + ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" + echo "artifacts-url=${ARTIFACTS_URL}" >> $GITHUB_OUTPUT + echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" + echo "" + echo "Upload Status Summary:" + echo "- IPA: ${{ steps.upload-ipa.outcome }}" + echo "- Archive: ${{ steps.upload-archive.outcome }}" + echo "- Source Map: ${{ steps.upload-sourcemap.outcome }}" + env: + GITHUB_REPOSITORY: ${{ github.repository }} + GITHUB_RUN_ID: ${{ github.run_id }} \ No newline at end of file From 94b070c5548f60aed034d62cb81a879004533886 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Mon, 28 Jul 2025 11:56:42 +0200 Subject: [PATCH 11/63] chore: add missing env vars for the build step --- .github/workflows/test-android-build-app.yml | 1 + .github/workflows/test-ios-build-app.yml | 17 +++++++++++++++++ 2 files changed, 18 insertions(+) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 7badbf23067..e16c6ab6822 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -10,6 +10,7 @@ permissions: jobs: android-build: + name: Test Android Build QA App runs-on: ubuntu-latest outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 14d48fab312..f584617ff81 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -104,6 +104,23 @@ jobs: GITHUB_CI: "true" CI: "true" + + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + - name: Upload iOS IPA Artifact id: upload-ipa uses: actions/upload-artifact@v4 From 6aa089f4f57fafbcedcfcffe20ee7887644aef20 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Mon, 28 Jul 2025 13:10:27 +0200 Subject: [PATCH 12/63] chore: simplify upload --- .github/workflows/test-android-build-app.yml | 25 ++------------------ .github/workflows/test-ios-build-app.yml | 25 ++------------------ 2 files changed, 4 insertions(+), 46 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index e16c6ab6822..c103d8ecd61 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -107,26 +107,6 @@ jobs: if-no-files-found: error continue-on-error: true - - name: Upload Android AAB Artifact - id: upload-aab - uses: actions/upload-artifact@v4 - with: - name: android-bundle-qa - path: android/app/build/outputs/bundle/qaRelease/app-qa-release.aab - retention-days: 7 - if-no-files-found: warn - continue-on-error: true - - - name: Upload Android Source Map - id: upload-sourcemap - uses: actions/upload-artifact@v4 - with: - name: android-sourcemap-qa - path: sourcemaps/android/index.android.bundle.map - retention-days: 7 - if-no-files-found: warn - continue-on-error: true - - name: Set Artifacts URL and Status id: set-artifacts-url run: | @@ -135,9 +115,8 @@ jobs: echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" echo "" echo "Upload Status Summary:" - echo "- APK: ${{ steps.upload-apk.outcome }}" - echo "- AAB Bundle: ${{ steps.upload-aab.outcome }}" - echo "- Source Map: ${{ steps.upload-sourcemap.outcome }}" + echo "- ๐Ÿค– APK: ${{ steps.upload-apk.outcome }}" + env: GITHUB_REPOSITORY: ${{ github.repository }} GITHUB_RUN_ID: ${{ github.run_id }} diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index f584617ff81..866776c41fa 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -131,26 +131,6 @@ jobs: if-no-files-found: error continue-on-error: true - - name: Upload iOS Archive Artifact - id: upload-archive - uses: actions/upload-artifact@v4 - with: - name: ios-archive-qa - path: ios/build/MetaMask-QA.xcarchive - retention-days: 7 - if-no-files-found: warn - continue-on-error: true - - - name: Upload iOS Source Map - id: upload-sourcemap - uses: actions/upload-artifact@v4 - with: - name: ios-sourcemap-qa - path: sourcemaps/ios/index.js.map - retention-days: 7 - if-no-files-found: warn - continue-on-error: true - - name: Set Artifacts URL and Status id: set-artifacts-url run: | @@ -159,9 +139,8 @@ jobs: echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" echo "" echo "Upload Status Summary:" - echo "- IPA: ${{ steps.upload-ipa.outcome }}" - echo "- Archive: ${{ steps.upload-archive.outcome }}" - echo "- Source Map: ${{ steps.upload-sourcemap.outcome }}" + echo "- ๏ฃฟ IPA: ${{ steps.upload-ipa.outcome }}" + env: GITHUB_REPOSITORY: ${{ github.repository }} GITHUB_RUN_ID: ${{ github.run_id }} \ No newline at end of file From 4be3d1450efeacbf5e55bcc93e5fbb64c6cb5283 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Mon, 28 Jul 2025 13:56:04 +0200 Subject: [PATCH 13/63] chore: build pods --- .github/workflows/test-ios-build-app.yml | 31 +----------------------- scripts/setup.mjs | 2 +- 2 files changed, 2 insertions(+), 31 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 866776c41fa..0cc35462531 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -62,37 +62,9 @@ jobs: shell: bash - name: Setup iOS Environment - run: | - yarn setup --build-on-github-ci --build-ios --no-build-android - shell: bash - env: - PLATFORM: ios - METAMASK_ENVIRONMENT: qa - METAMASK_BUILD_TYPE: main - IS_TEST: true - IGNORE_BOXLOGS_DEVELOPMENT: true - GITHUB_CI: "true" - CI: "true" - - SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} - SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} - SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} - SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} - - MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} - MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} - - MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} - MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} - MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} - GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} - GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} - - - name: Build iOS App run: | echo "๐Ÿš€ Building iOS APP..." + yarn setup --build-on-github-ci --build-ios --no-build-android yarn build:ios:qa shell: bash env: @@ -104,7 +76,6 @@ jobs: GITHUB_CI: "true" CI: "true" - SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} diff --git a/scripts/setup.mjs b/scripts/setup.mjs index d394254b68d..ab12fe68c1d 100644 --- a/scripts/setup.mjs +++ b/scripts/setup.mjs @@ -196,7 +196,7 @@ const setupIosTask = { }, ]; - if (INSTALL_PODS && !GITHUB_CI) { + if (INSTALL_PODS) { tasks.push({ title: 'Install CocoaPods', task: async () => { From 58b5872be7da9f69ec790f19d15b1c061c26f9fb Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Mon, 28 Jul 2025 17:09:16 +0200 Subject: [PATCH 14/63] chore: set node memory limit to avoid OOO issue --- .github/workflows/test-ios-build-app.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 0cc35462531..f07b1cebf09 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -76,6 +76,8 @@ jobs: GITHUB_CI: "true" CI: "true" + NODE_OPTIONS: "--max_old_space_size=4096" + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} From a76d156fd384b72968fb23eb1faa62c6fdd38b2e Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Tue, 29 Jul 2025 09:45:46 +0200 Subject: [PATCH 15/63] chore: added ipa app source map as optional Also comment a block to test if we can save 4 minutes of pipeline --- .github/workflows/test-ios-build-app.yml | 58 ++++++++++++++++++++---- 1 file changed, 48 insertions(+), 10 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index f07b1cebf09..fa2a4d0e9b1 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -13,6 +13,7 @@ jobs: runs-on: macos-15 outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} + app-uploaded: ${{ steps.upload-app.outcome == 'success' }} ipa-uploaded: ${{ steps.upload-ipa.outcome == 'success' }} archive-uploaded: ${{ steps.upload-archive.outcome == 'success' }} sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} @@ -41,11 +42,11 @@ jobs: sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' shell: bash - - name: Setup E2E iOS Environment - uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - with: - platform: ios - setup-simulator: false + # - name: Installing iOS Environment Setup + # uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + # with: + # platform: ios + # setup-simulator: false - name: Print iOS tool versions run: | @@ -63,8 +64,9 @@ jobs: - name: Setup iOS Environment run: | - echo "๐Ÿš€ Building iOS APP..." + echo "๐Ÿš€ Finishing iOS Setup..." yarn setup --build-on-github-ci --build-ios --no-build-android + echo "๐Ÿ— Building iOS APP..." yarn build:ios:qa shell: bash env: @@ -94,14 +96,47 @@ jobs: GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} - - name: Upload iOS IPA Artifact + - name: Upload iOS APP Artifact (Simulator) + id: upload-app + uses: actions/upload-artifact@v4 + with: + name: ios-app-qa-simulator + path: ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app + retention-days: 7 + if-no-files-found: error + continue-on-error: true + + # Won't exist without certificates + - name: Upload iOS IPA Artifact (Device) id: upload-ipa uses: actions/upload-artifact@v4 with: - name: ios-app-qa + name: ios-ipa-qa-device path: ios/build/output/MetaMask-QA.ipa retention-days: 7 - if-no-files-found: error + if-no-files-found: warn + continue-on-error: true + + # Won't exist for simulator builds + - name: Upload iOS Archive Artifact + id: upload-archive + uses: actions/upload-artifact@v4 + with: + name: ios-archive-qa + path: ios/build/MetaMask-QA.xcarchive + retention-days: 7 + if-no-files-found: warn + continue-on-error: true + + # May not always exist, so we continue-on-error + - name: Upload iOS Source Map + id: upload-sourcemap + uses: actions/upload-artifact@v4 + with: + name: ios-sourcemap-qa + path: sourcemaps/ios/index.js.map + retention-days: 7 + if-no-files-found: warn continue-on-error: true - name: Set Artifacts URL and Status @@ -112,7 +147,10 @@ jobs: echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" echo "" echo "Upload Status Summary:" - echo "- ๏ฃฟ IPA: ${{ steps.upload-ipa.outcome }}" + echo "- ๏ฃฟ APP (Simulator): ${{ steps.upload-app.outcome }}" + echo "- ๏ฃฟ IPA (Device): ${{ steps.upload-ipa.outcome }}" + echo "- ๏ฃฟ Archive: ${{ steps.upload-archive.outcome }}" + echo "- ๏ฃฟ Source Map: ${{ steps.upload-sourcemap.outcome }}" env: GITHUB_REPOSITORY: ${{ github.repository }} From d3facfbd643c21fe5914fe094530b04da543c6fd Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Tue, 29 Jul 2025 09:49:52 +0200 Subject: [PATCH 16/63] chore: we need to run the env setup as figured --- .github/workflows/test-ios-build-app.yml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index fa2a4d0e9b1..19990ede34e 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -42,11 +42,11 @@ jobs: sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' shell: bash - # - name: Installing iOS Environment Setup - # uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - # with: - # platform: ios - # setup-simulator: false + - name: Installing iOS Environment Setup + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + with: + platform: ios + setup-simulator: false - name: Print iOS tool versions run: | From 4a41c3ef82cafec4780e15f8fbdf6345d5f0fa35 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Tue, 29 Jul 2025 11:59:50 +0200 Subject: [PATCH 17/63] chore: improved legibility and structure --- .github/workflows/test-android-build-app.yml | 46 +++++++++++++++++--- .github/workflows/test-ios-build-app.yml | 37 +++++++++++----- 2 files changed, 66 insertions(+), 17 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index c103d8ecd61..e7ba4bb85b5 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -2,6 +2,13 @@ name: Test Android Build QA App on: push: + workflow_dispatch: + inputs: + retention_days: + description: 'Number of days to retain artifacts' + required: false + default: '7' + type: string permissions: @@ -18,17 +25,18 @@ jobs: aab-uploaded: ${{ steps.upload-aab.outcome == 'success' }} sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} steps: + # Get the source code from the repository - name: Checkout repo uses: actions/checkout@v4 - + # Install Android SDK, Node.js, and other Android development dependencies - name: Setup E2E Android Environment uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions with: platform: android setup-simulator: false - + # Display Android development tools information for debugging - name: Print Android Environment Info run: | echo "๐Ÿ”ง Node.js Version:" @@ -66,10 +74,12 @@ jobs: adb devices || echo "adb devices failed" shell: bash - - name: Build Android App + # Run project setup and build the Android QA app (APK and AAB) + - name: Setup Android Environment run: | - echo "๐Ÿš€ Building Android APP..." + echo "๐Ÿš€ Finishing Android Setup..." yarn setup:github-ci --no-build-ios + echo "๐Ÿ— Building Android APP..." yarn build:android:qa shell: bash env: @@ -97,16 +107,40 @@ jobs: GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + # Upload the Android APK file for device installation and testing - name: Upload Android APK Artifact id: upload-apk uses: actions/upload-artifact@v4 with: name: android-app-qa path: android/app/build/outputs/apk/qa/release/app-qa-release.apk - retention-days: 7 + retention-days: ${{ inputs.retention_days }} if-no-files-found: error continue-on-error: true + # Upload the Android App Bundle (AAB) for Play Store distribution + - name: Upload Android AAB Artifact + id: upload-aab + uses: actions/upload-artifact@v4 + with: + name: android-bundle-qa + path: android/app/build/outputs/bundle/qaRelease/app-qa-release.aab + retention-days: ${{ inputs.retention_days }} + if-no-files-found: warn + continue-on-error: true + + # Upload source map file for crash debugging and error tracking + - name: Upload Android Source Map + id: upload-sourcemap + uses: actions/upload-artifact@v4 + with: + name: android-sourcemap-qa + path: sourcemaps/android/index.android.bundle.map + retention-days: ${{ inputs.retention_days }} + if-no-files-found: warn + continue-on-error: true + + # Generate artifact download URL and display upload status summary - name: Set Artifacts URL and Status id: set-artifacts-url run: | @@ -116,6 +150,8 @@ jobs: echo "" echo "Upload Status Summary:" echo "- ๐Ÿค– APK: ${{ steps.upload-apk.outcome }}" + echo "- ๐Ÿ“ฆ AAB Bundle: ${{ steps.upload-aab.outcome }}" + echo "- ๐Ÿ“ฆ Source Map: ${{ steps.upload-sourcemap.outcome }}" env: GITHUB_REPOSITORY: ${{ github.repository }} diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 19990ede34e..a22c9a34fc3 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -2,6 +2,13 @@ name: Test iOS Build QA App on: push: + workflow_dispatch: + inputs: + retention_days: + description: 'Number of days to retain the uploaded artifacts' + required: false + default: '7' + type: string permissions: contents: write @@ -20,9 +27,11 @@ jobs: env: GITHUB_CI: "true" # โœ… This ensures it's available during pod install steps: + # Get the source code from the repository - name: Checkout repo uses: actions/checkout@v4 + # Display system information for debugging purposes - name: Detect CPU architecture run: | echo "Arch: $(uname -m)" @@ -42,6 +51,7 @@ jobs: sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' shell: bash + # Install Node.js, Xcode tools, and other iOS development dependencies - name: Installing iOS Environment Setup uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions with: @@ -62,10 +72,11 @@ jobs: xcrun simctl list | grep Booted || echo "No booted simulators found" shell: bash + # Run project setup and build the iOS QA app for simulator - name: Setup iOS Environment run: | echo "๐Ÿš€ Finishing iOS Setup..." - yarn setup --build-on-github-ci --build-ios --no-build-android + yarn setup:github-ci --build-ios --no-build-android echo "๐Ÿ— Building iOS APP..." yarn build:ios:qa shell: bash @@ -78,7 +89,7 @@ jobs: GITHUB_CI: "true" CI: "true" - NODE_OPTIONS: "--max_old_space_size=4096" + NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} @@ -96,49 +107,51 @@ jobs: GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + # Upload the iOS .app file that works in simulators (no certificates needed) - name: Upload iOS APP Artifact (Simulator) id: upload-app uses: actions/upload-artifact@v4 with: name: ios-app-qa-simulator path: ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app - retention-days: 7 + retention-days: ${{ inputs.retention_days }} if-no-files-found: error continue-on-error: true - # Won't exist without certificates + # Upload iOS .ipa file for device installation (requires certificates - may not exist) - name: Upload iOS IPA Artifact (Device) id: upload-ipa uses: actions/upload-artifact@v4 with: name: ios-ipa-qa-device path: ios/build/output/MetaMask-QA.ipa - retention-days: 7 - if-no-files-found: warn + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error continue-on-error: true - # Won't exist for simulator builds + # Upload iOS .xcarchive file for debugging and re-signing (requires certificates - may not exist) - name: Upload iOS Archive Artifact id: upload-archive uses: actions/upload-artifact@v4 with: name: ios-archive-qa path: ios/build/MetaMask-QA.xcarchive - retention-days: 7 - if-no-files-found: warn + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error continue-on-error: true - # May not always exist, so we continue-on-error + # Upload source map file for crash debugging and error tracking if exists - name: Upload iOS Source Map id: upload-sourcemap uses: actions/upload-artifact@v4 with: name: ios-sourcemap-qa path: sourcemaps/ios/index.js.map - retention-days: 7 - if-no-files-found: warn + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error continue-on-error: true + # Generate artifact download URL and display upload status summary - name: Set Artifacts URL and Status id: set-artifacts-url run: | From de4e08e2b3676a512b30b3ba0a108eb9582301d5 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Tue, 29 Jul 2025 13:10:13 +0200 Subject: [PATCH 18/63] chore: fix shellcheck --- .github/workflows/test-android-build-app.yml | 6 +++--- .github/workflows/test-ios-build-app.yml | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index e7ba4bb85b5..69cf44af89c 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -30,7 +30,7 @@ jobs: uses: actions/checkout@v4 # Install Android SDK, Node.js, and other Android development dependencies - - name: Setup E2E Android Environment + - name: Installing Android Environment Setup uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions with: platform: android @@ -154,5 +154,5 @@ jobs: echo "- ๐Ÿ“ฆ Source Map: ${{ steps.upload-sourcemap.outcome }}" env: - GITHUB_REPOSITORY: ${{ github.repository }} - GITHUB_RUN_ID: ${{ github.run_id }} + GITHUB_REPOSITORY: "${{ github.repository }}" + GITHUB_RUN_ID: "${{ github.run_id }}" diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index a22c9a34fc3..82053c06e7e 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -166,5 +166,5 @@ jobs: echo "- ๏ฃฟ Source Map: ${{ steps.upload-sourcemap.outcome }}" env: - GITHUB_REPOSITORY: ${{ github.repository }} - GITHUB_RUN_ID: ${{ github.run_id }} \ No newline at end of file + GITHUB_REPOSITORY: "${{ github.repository }}" + GITHUB_RUN_ID: "${{ github.run_id }}" \ No newline at end of file From 3f87b95701b5893b19cba4f080c908305551e64f Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Tue, 29 Jul 2025 13:24:17 +0200 Subject: [PATCH 19/63] chore: add quotes to github output id --- .github/workflows/test-android-build-app.yml | 2 +- .github/workflows/test-ios-build-app.yml | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 69cf44af89c..88dfca1ae9d 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -2,7 +2,7 @@ name: Test Android Build QA App on: push: - workflow_dispatch: + workflow_call: inputs: retention_days: description: 'Number of days to retain artifacts' diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 82053c06e7e..c94a1ab2938 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -2,7 +2,7 @@ name: Test iOS Build QA App on: push: - workflow_dispatch: + workflow_call: inputs: retention_days: description: 'Number of days to retain the uploaded artifacts' @@ -156,7 +156,7 @@ jobs: id: set-artifacts-url run: | ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" - echo "artifacts-url=${ARTIFACTS_URL}" >> $GITHUB_OUTPUT + echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" echo "" echo "Upload Status Summary:" From b55e5a32e929796c35339d26c95822feb697d0b2 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Tue, 29 Jul 2025 13:39:11 +0200 Subject: [PATCH 20/63] chore: set proper name to artifacts cursor changed them --- .github/workflows/test-android-build-app.yml | 11 +++++------ .github/workflows/test-ios-build-app.yml | 10 +++++----- 2 files changed, 10 insertions(+), 11 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 88dfca1ae9d..6fdca1aa78e 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -2,7 +2,7 @@ name: Test Android Build QA App on: push: - workflow_call: + workflow_dispatch: inputs: retention_days: description: 'Number of days to retain artifacts' @@ -10,7 +10,6 @@ on: default: '7' type: string - permissions: contents: write id-token: write @@ -112,7 +111,7 @@ jobs: id: upload-apk uses: actions/upload-artifact@v4 with: - name: android-app-qa + name: app-qa-release.apk path: android/app/build/outputs/apk/qa/release/app-qa-release.apk retention-days: ${{ inputs.retention_days }} if-no-files-found: error @@ -123,7 +122,7 @@ jobs: id: upload-aab uses: actions/upload-artifact@v4 with: - name: android-bundle-qa + name: app-qa-release.aab path: android/app/build/outputs/bundle/qaRelease/app-qa-release.aab retention-days: ${{ inputs.retention_days }} if-no-files-found: warn @@ -134,7 +133,7 @@ jobs: id: upload-sourcemap uses: actions/upload-artifact@v4 with: - name: android-sourcemap-qa + name: index.android.bundle.map path: sourcemaps/android/index.android.bundle.map retention-days: ${{ inputs.retention_days }} if-no-files-found: warn @@ -145,7 +144,7 @@ jobs: id: set-artifacts-url run: | ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" - echo "artifacts-url=${ARTIFACTS_URL}" >> $GITHUB_OUTPUT + echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" echo "" echo "Upload Status Summary:" diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index c94a1ab2938..bdcd1d10c0d 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -2,7 +2,7 @@ name: Test iOS Build QA App on: push: - workflow_call: + workflow_dispatch: inputs: retention_days: description: 'Number of days to retain the uploaded artifacts' @@ -112,7 +112,7 @@ jobs: id: upload-app uses: actions/upload-artifact@v4 with: - name: ios-app-qa-simulator + name: MetaMask-QA.app path: ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app retention-days: ${{ inputs.retention_days }} if-no-files-found: error @@ -123,7 +123,7 @@ jobs: id: upload-ipa uses: actions/upload-artifact@v4 with: - name: ios-ipa-qa-device + name: MetaMask-QA.ipa path: ios/build/output/MetaMask-QA.ipa retention-days: ${{ inputs.retention_days }} if-no-files-found: error @@ -134,7 +134,7 @@ jobs: id: upload-archive uses: actions/upload-artifact@v4 with: - name: ios-archive-qa + name: MetaMask-QA.xcarchive path: ios/build/MetaMask-QA.xcarchive retention-days: ${{ inputs.retention_days }} if-no-files-found: error @@ -145,7 +145,7 @@ jobs: id: upload-sourcemap uses: actions/upload-artifact@v4 with: - name: ios-sourcemap-qa + name: index.js.map path: sourcemaps/ios/index.js.map retention-days: ${{ inputs.retention_days }} if-no-files-found: error From eaf3096812e81b580d9b2837f657eea4a62e7ba4 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Wed, 30 Jul 2025 11:58:38 +0200 Subject: [PATCH 21/63] chore: test self hosted nodes --- .github/workflows/test-android-build-app.yml | 3 ++- .github/workflows/test-ios-build-app.yml | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 6fdca1aa78e..4a36b21c51d 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -17,7 +17,8 @@ permissions: jobs: android-build: name: Test Android Build QA App - runs-on: ubuntu-latest + # runs-on: ubuntu-latest + runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index bdcd1d10c0d..b92d458e4c5 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -17,7 +17,8 @@ permissions: jobs: ios-build: name: Test iOS QA Build App - runs-on: macos-15 + # runs-on: macos-15 + runs-on: [self-hosted, macOS, metamask-mobile] outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} app-uploaded: ${{ steps.upload-app.outcome == 'success' }} From 789052acd2d3c9f01a31d25cbb2429dc5debbcf3 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Wed, 30 Jul 2025 12:19:52 +0200 Subject: [PATCH 22/63] chore: test different branch for self hosted runners --- .github/workflows/test-android-build-app.yml | 3 ++- .github/workflows/test-ios-build-app.yml | 3 +-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 4a36b21c51d..36a9edde5c2 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -31,7 +31,8 @@ jobs: # Install Android SDK, Node.js, and other Android development dependencies - name: Installing Android Environment Setup - uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + # uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@self-hosted-runners-config with: platform: android setup-simulator: false diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index b92d458e4c5..bdcd1d10c0d 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -17,8 +17,7 @@ permissions: jobs: ios-build: name: Test iOS QA Build App - # runs-on: macos-15 - runs-on: [self-hosted, macOS, metamask-mobile] + runs-on: macos-15 outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} app-uploaded: ${{ steps.upload-app.outcome == 'success' }} From be0fca46aeeb9bc188cfebf1f921775d970836d4 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 09:59:29 +0200 Subject: [PATCH 23/63] chore: test xl android instance for test And disabled ios temporary --- .github/workflows/test-android-build-app.yml | 2 +- .github/workflows/test-ios-build-app.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 36a9edde5c2..98f434c8f77 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -18,7 +18,7 @@ jobs: android-build: name: Test Android Build QA App # runs-on: ubuntu-latest - runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large + runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-xl outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index bdcd1d10c0d..5484715b6f4 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -1,7 +1,7 @@ name: Test iOS Build QA App on: - push: +# push: workflow_dispatch: inputs: retention_days: From 84a0cddaac015bf591cb199d7d6047336c95900b Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 10:02:17 +0200 Subject: [PATCH 24/63] chore: test --- .github/workflows/test-android-build-app.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 98f434c8f77..36a9edde5c2 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -18,7 +18,7 @@ jobs: android-build: name: Test Android Build QA App # runs-on: ubuntu-latest - runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-xl + runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} From 1164b830316dc813b52271e9005860b5c4dc3f89 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 10:39:33 +0200 Subject: [PATCH 25/63] chore: test some gradle limits for selfhosted --- .github/workflows/test-android-build-app.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 36a9edde5c2..f3992000bba 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -92,6 +92,9 @@ jobs: GITHUB_CI: "true" CI: "true" + GRADLE_OPTS: "-Xmx20480m -Dorg.gradle.jvmargs='-Xmx20480m -XX:MaxPermSize=64m'" + NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} From 468c92c89f9f5ec7a7a044d37aff78fe51113f0a Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 10:50:27 +0200 Subject: [PATCH 26/63] chore: remove maxpermsize option --- .github/workflows/test-android-build-app.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index f3992000bba..49cb216c297 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -92,7 +92,7 @@ jobs: GITHUB_CI: "true" CI: "true" - GRADLE_OPTS: "-Xmx20480m -Dorg.gradle.jvmargs='-Xmx20480m -XX:MaxPermSize=64m'" + GRADLE_OPTS: "-Xmx20480m -Dorg.gradle.jvmargs='-Xmx20480m'" NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} From e5da965ec2f18cd2bbb4b3813c16848c25fa9a62 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 11:50:50 +0200 Subject: [PATCH 27/63] chore: set memory limit --- .github/workflows/test-android-build-app.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 49cb216c297..e38968f42e7 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -93,7 +93,7 @@ jobs: CI: "true" GRADLE_OPTS: "-Xmx20480m -Dorg.gradle.jvmargs='-Xmx20480m'" - NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners + NODE_OPTIONS: "--max-old-space-size=4096" # Increase memory limit for build, specially on GH Runners SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} From 2ffb430370718c9b11e9c7e65c9030b1fee544aa Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 12:10:25 +0200 Subject: [PATCH 28/63] chore: another limit --- .github/workflows/test-android-build-app.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index e38968f42e7..d1f48e8e76e 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -81,6 +81,7 @@ jobs: echo "๐Ÿš€ Finishing Android Setup..." yarn setup:github-ci --no-build-ios echo "๐Ÿ— Building Android APP..." + export NODE_OPTIONS="--max-old-space-size=4096" yarn build:android:qa shell: bash env: @@ -92,7 +93,7 @@ jobs: GITHUB_CI: "true" CI: "true" - GRADLE_OPTS: "-Xmx20480m -Dorg.gradle.jvmargs='-Xmx20480m'" + GRADLE_OPTS: "-Xmx4096m -Dorg.gradle.jvmargs='-Xmx4096m'" NODE_OPTIONS: "--max-old-space-size=4096" # Increase memory limit for build, specially on GH Runners SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} From 793f0393c04317017f4460f4eb25c1be19bd1830 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 12:49:03 +0200 Subject: [PATCH 29/63] chore: test limit memory gradle parallel arch --- .github/workflows/test-android-build-app.yml | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index d1f48e8e76e..6778f30169a 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -81,7 +81,8 @@ jobs: echo "๐Ÿš€ Finishing Android Setup..." yarn setup:github-ci --no-build-ios echo "๐Ÿ— Building Android APP..." - export NODE_OPTIONS="--max-old-space-size=4096" + export NODE_OPTIONS="--max-old-space-size=2048" + export GRADLE_OPTS="-Xmx6g -Dorg.gradle.workers.max=2" yarn build:android:qa shell: bash env: @@ -93,8 +94,8 @@ jobs: GITHUB_CI: "true" CI: "true" - GRADLE_OPTS: "-Xmx4096m -Dorg.gradle.jvmargs='-Xmx4096m'" - NODE_OPTIONS: "--max-old-space-size=4096" # Increase memory limit for build, specially on GH Runners + NODE_OPTIONS: "--max-old-space-size=2048" + GRADLE_OPTS: "-Xmx6g -Dorg.gradle.jvmargs='-Xmx6g' -Dorg.gradle.workers.max=2" SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} From f14941889a38ac069783e058f22dadea8e08feb7 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 15:49:50 +0200 Subject: [PATCH 30/63] chore: test xl self hosted --- .github/workflows/test-android-build-app.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 6778f30169a..cac6bd9f44f 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -18,7 +18,7 @@ jobs: android-build: name: Test Android Build QA App # runs-on: ubuntu-latest - runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large + runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-xl outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} From ed308a0b9a49cc48661fe73b3c24f1d5bea7d119 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 15:51:37 +0200 Subject: [PATCH 31/63] chore: use xl mmsdk --- .github/workflows/test-android-build-app.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index cac6bd9f44f..9125a5b66f5 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -18,7 +18,8 @@ jobs: android-build: name: Test Android Build QA App # runs-on: ubuntu-latest - runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-xl + #runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large + runs-on: gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl outputs: artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} From 3090d417847d59b11a1c53d4e206f58caa92c066 Mon Sep 17 00:00:00 2001 From: Alejandro Som <560018+alucardzom@users.noreply.github.com> Date: Thu, 31 Jul 2025 17:16:51 +0200 Subject: [PATCH 32/63] chore: try to use gradle_opts variables --- .github/workflows/test-android-build-app.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 9125a5b66f5..b243a1f5934 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -17,7 +17,6 @@ permissions: jobs: android-build: name: Test Android Build QA App - # runs-on: ubuntu-latest #runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large runs-on: gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl outputs: From 75df40195950e64f85bfcbe65362a91b7f9d4587 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 10:47:56 +0100 Subject: [PATCH 33/63] gradle configs --- .github/workflows/test-android-build-app.yml | 8 ++++---- android/gradle.properties | 11 +++++++++-- 2 files changed, 13 insertions(+), 6 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index b243a1f5934..7f8d4ea70e6 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -81,8 +81,8 @@ jobs: echo "๐Ÿš€ Finishing Android Setup..." yarn setup:github-ci --no-build-ios echo "๐Ÿ— Building Android APP..." - export NODE_OPTIONS="--max-old-space-size=2048" - export GRADLE_OPTS="-Xmx6g -Dorg.gradle.workers.max=2" + export NODE_OPTIONS="--max-old-space-size=8192" + export GRADLE_OPTS="-Xmx32g -Dorg.gradle.workers.max=12 -Dorg.gradle.parallel=true -Dorg.gradle.caching=true" yarn build:android:qa shell: bash env: @@ -94,8 +94,8 @@ jobs: GITHUB_CI: "true" CI: "true" - NODE_OPTIONS: "--max-old-space-size=2048" - GRADLE_OPTS: "-Xmx6g -Dorg.gradle.jvmargs='-Xmx6g' -Dorg.gradle.workers.max=2" + NODE_OPTIONS: "--max-old-space-size=8192" + GRADLE_OPTS: "-Xmx32g -Dorg.gradle.jvmargs='-Xmx32g -XX:+UseG1GC' -Dorg.gradle.workers.max=12 -Dorg.gradle.parallel=true -Dorg.gradle.caching=true" SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} diff --git a/android/gradle.properties b/android/gradle.properties index 7dfb8c44ffa..6c1a820d25e 100644 --- a/android/gradle.properties +++ b/android/gradle.properties @@ -10,12 +10,19 @@ # Specifies the JVM arguments used for the daemon process. # The setting is particularly useful for tweaking memory settings. # Default value: -Xmx512m -XX:MaxMetaspaceSize=256m -org.gradle.jvmargs=-Xmx4g -XX:MaxMetaspaceSize=512m +org.gradle.jvmargs=-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC # When configured, Gradle will run in incubating parallel mode. # This option should only be used with decoupled projects. More details, visit # http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects -# org.gradle.parallel=true +org.gradle.parallel=true + +# Additional performance optimizations +org.gradle.configureondemand=true +org.gradle.caching=true +org.gradle.daemon=true +org.gradle.workers.max=12 +org.gradle.vfs.watch=true # AndroidX package structure to make it clearer which packages are bundled with the # Android operating system, and which are packaged with your app's APK From e0d12df1a9d4c1957a1942f0063746c59f6a7c10 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 11:52:19 +0100 Subject: [PATCH 34/63] more gradle configs --- android/gradle.properties | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/android/gradle.properties b/android/gradle.properties index 6c1a820d25e..602d54eb828 100644 --- a/android/gradle.properties +++ b/android/gradle.properties @@ -10,7 +10,7 @@ # Specifies the JVM arguments used for the daemon process. # The setting is particularly useful for tweaking memory settings. # Default value: -Xmx512m -XX:MaxMetaspaceSize=256m -org.gradle.jvmargs=-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC +# JVM args configured below with additional G1GC optimizations # When configured, Gradle will run in incubating parallel mode. # This option should only be used with decoupled projects. More details, visit @@ -24,6 +24,20 @@ org.gradle.daemon=true org.gradle.workers.max=12 org.gradle.vfs.watch=true +# Additional CI optimizations +# org.gradle.unsafe.configuration-cache=true # Disabled - incompatible with Expo/RN +# org.gradle.unsafe.configuration-cache-problems=warn +kotlin.incremental=true +kotlin.incremental.android=true +kotlin.caching.enabled=true + +# File system optimizations +org.gradle.vfs.verbose=false +org.gradle.welcome=never + +# JVM optimizations +org.gradle.jvmargs=-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC -XX:G1HeapRegionSize=32m -XX:+UseStringDeduplication -XX:+OptimizeStringConcat + # AndroidX package structure to make it clearer which packages are bundled with the # Android operating system, and which are packaged with your app's APK # https://developer.android.com/topic/libraries/support-library/androidx-rn From 34677c4f4a7ff7567b44b54cd3332cb86ebe0c33 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 13:44:54 +0100 Subject: [PATCH 35/63] gradle for bitrrise and gha --- android/gradle.properties | 44 +++++++++++++++++++-------------------- 1 file changed, 21 insertions(+), 23 deletions(-) diff --git a/android/gradle.properties b/android/gradle.properties index 602d54eb828..ec35a126428 100644 --- a/android/gradle.properties +++ b/android/gradle.properties @@ -10,39 +10,37 @@ # Specifies the JVM arguments used for the daemon process. # The setting is particularly useful for tweaking memory settings. # Default value: -Xmx512m -XX:MaxMetaspaceSize=256m -# JVM args configured below with additional G1GC optimizations -# When configured, Gradle will run in incubating parallel mode. -# This option should only be used with decoupled projects. More details, visit -# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects -org.gradle.parallel=true +# Environment-based JVM configuration +# GitHub Actions (GITHUB_ACTIONS=true): High-performance settings for 64GB/16CPU runners +# Bitrise (default): Conservative settings for existing infrastructure +org.gradle.jvmargs=${GITHUB_ACTIONS:+-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC -XX:G1HeapRegionSize=32m -XX:+UseStringDeduplication -XX:+OptimizeStringConcat}${GITHUB_ACTIONS:-Xmx4g -XX:MaxMetaspaceSize=512m} -# Additional performance optimizations -org.gradle.configureondemand=true -org.gradle.caching=true -org.gradle.daemon=true -org.gradle.workers.max=12 -org.gradle.vfs.watch=true +# Parallel builds - enabled for GitHub Actions, disabled for Bitrise +org.gradle.parallel=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -# Additional CI optimizations -# org.gradle.unsafe.configuration-cache=true # Disabled - incompatible with Expo/RN -# org.gradle.unsafe.configuration-cache-problems=warn -kotlin.incremental=true -kotlin.incremental.android=true -kotlin.caching.enabled=true +# Additional performance optimizations for GitHub Actions +org.gradle.configureondemand=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} +org.gradle.caching=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} +org.gradle.daemon=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} +org.gradle.workers.max=${GITHUB_ACTIONS:+12}${GITHUB_ACTIONS:-2} +org.gradle.vfs.watch=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -# File system optimizations -org.gradle.vfs.verbose=false -org.gradle.welcome=never +# CI-specific optimizations for GitHub Actions +kotlin.incremental=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} +kotlin.incremental.android=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} +kotlin.caching.enabled=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -# JVM optimizations -org.gradle.jvmargs=-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC -XX:G1HeapRegionSize=32m -XX:+UseStringDeduplication -XX:+OptimizeStringConcat +# File system optimizations for GitHub Actions +org.gradle.vfs.verbose=${GITHUB_ACTIONS:+false}${GITHUB_ACTIONS:-true} +org.gradle.welcome=${GITHUB_ACTIONS:+never}${GITHUB_ACTIONS:-once} # AndroidX package structure to make it clearer which packages are bundled with the # Android operating system, and which are packaged with your app's APK # https://developer.android.com/topic/libraries/support-library/androidx-rn android.useAndroidX=true android.enableJetifier=true + # Enable AAPT2 PNG crunching android.enablePngCrunchInReleaseBuilds=true @@ -69,4 +67,4 @@ hermesEnabled=true android.disableResourceValidation=true # Use legacy packaging to compress native libraries in the resulting APK. -expo.useLegacyPackaging=false +expo.useLegacyPackaging=false From a50b491e5b3b8faba6842e002303e43f70d54ee8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 13:55:31 +0100 Subject: [PATCH 36/63] caps --- android/gradle.properties | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/android/gradle.properties b/android/gradle.properties index ec35a126428..061aa4c5707 100644 --- a/android/gradle.properties +++ b/android/gradle.properties @@ -33,7 +33,7 @@ kotlin.caching.enabled=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} # File system optimizations for GitHub Actions org.gradle.vfs.verbose=${GITHUB_ACTIONS:+false}${GITHUB_ACTIONS:-true} -org.gradle.welcome=${GITHUB_ACTIONS:+never}${GITHUB_ACTIONS:-once} +org.gradle.welcome=${GITHUB_ACTIONS:+NEVER}${GITHUB_ACTIONS:-ONCE} # AndroidX package structure to make it clearer which packages are bundled with the # Android operating system, and which are packaged with your app's APK From 7b44107dd0a62d370bcf6d14c1f6b36714a8543a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 14:13:57 +0100 Subject: [PATCH 37/63] try to override --- .github/workflows/test-android-build-app.yml | 15 ++++++++-- android/gradle.properties | 31 ++++---------------- 2 files changed, 19 insertions(+), 27 deletions(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 7f8d4ea70e6..5a9ac2cbb0f 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -82,7 +82,6 @@ jobs: yarn setup:github-ci --no-build-ios echo "๐Ÿ— Building Android APP..." export NODE_OPTIONS="--max-old-space-size=8192" - export GRADLE_OPTS="-Xmx32g -Dorg.gradle.workers.max=12 -Dorg.gradle.parallel=true -Dorg.gradle.caching=true" yarn build:android:qa shell: bash env: @@ -95,7 +94,19 @@ jobs: CI: "true" NODE_OPTIONS: "--max-old-space-size=8192" - GRADLE_OPTS: "-Xmx32g -Dorg.gradle.jvmargs='-Xmx32g -XX:+UseG1GC' -Dorg.gradle.workers.max=12 -Dorg.gradle.parallel=true -Dorg.gradle.caching=true" + GRADLE_OPTS: >- + -Porg.gradle.jvmargs="-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC -XX:G1HeapRegionSize=32m -XX:+UseStringDeduplication -XX:+OptimizeStringConcat" + -Porg.gradle.parallel=true + -Porg.gradle.configureondemand=true + -Porg.gradle.caching=true + -Porg.gradle.daemon=true + -Porg.gradle.workers.max=12 + -Porg.gradle.vfs.watch=true + -Pkotlin.incremental=true + -Pkotlin.incremental.android=true + -Pkotlin.caching.enabled=true + -Porg.gradle.vfs.verbose=false + -Porg.gradle.welcome=NEVER SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} diff --git a/android/gradle.properties b/android/gradle.properties index 061aa4c5707..7dfb8c44ffa 100644 --- a/android/gradle.properties +++ b/android/gradle.properties @@ -10,37 +10,18 @@ # Specifies the JVM arguments used for the daemon process. # The setting is particularly useful for tweaking memory settings. # Default value: -Xmx512m -XX:MaxMetaspaceSize=256m +org.gradle.jvmargs=-Xmx4g -XX:MaxMetaspaceSize=512m -# Environment-based JVM configuration -# GitHub Actions (GITHUB_ACTIONS=true): High-performance settings for 64GB/16CPU runners -# Bitrise (default): Conservative settings for existing infrastructure -org.gradle.jvmargs=${GITHUB_ACTIONS:+-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC -XX:G1HeapRegionSize=32m -XX:+UseStringDeduplication -XX:+OptimizeStringConcat}${GITHUB_ACTIONS:-Xmx4g -XX:MaxMetaspaceSize=512m} - -# Parallel builds - enabled for GitHub Actions, disabled for Bitrise -org.gradle.parallel=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} - -# Additional performance optimizations for GitHub Actions -org.gradle.configureondemand=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -org.gradle.caching=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -org.gradle.daemon=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -org.gradle.workers.max=${GITHUB_ACTIONS:+12}${GITHUB_ACTIONS:-2} -org.gradle.vfs.watch=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} - -# CI-specific optimizations for GitHub Actions -kotlin.incremental=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -kotlin.incremental.android=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} -kotlin.caching.enabled=${GITHUB_ACTIONS:+true}${GITHUB_ACTIONS:-false} - -# File system optimizations for GitHub Actions -org.gradle.vfs.verbose=${GITHUB_ACTIONS:+false}${GITHUB_ACTIONS:-true} -org.gradle.welcome=${GITHUB_ACTIONS:+NEVER}${GITHUB_ACTIONS:-ONCE} +# When configured, Gradle will run in incubating parallel mode. +# This option should only be used with decoupled projects. More details, visit +# http://www.gradle.org/docs/current/userguide/multi_project_builds.html#sec:decoupled_projects +# org.gradle.parallel=true # AndroidX package structure to make it clearer which packages are bundled with the # Android operating system, and which are packaged with your app's APK # https://developer.android.com/topic/libraries/support-library/androidx-rn android.useAndroidX=true android.enableJetifier=true - # Enable AAPT2 PNG crunching android.enablePngCrunchInReleaseBuilds=true @@ -67,4 +48,4 @@ hermesEnabled=true android.disableResourceValidation=true # Use legacy packaging to compress native libraries in the resulting APK. -expo.useLegacyPackaging=false +expo.useLegacyPackaging=false From 85305008f697bfa10fa4f4216303ec8461717fc2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 15:26:47 +0100 Subject: [PATCH 38/63] add gradle args --- .github/workflows/test-android-build-app.yml | 14 +---- android/github-init.gradle | 54 ++++++++++++++++++++ scripts/build.sh | 6 +-- 3 files changed, 58 insertions(+), 16 deletions(-) create mode 100644 android/github-init.gradle diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 5a9ac2cbb0f..d559c023c79 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -82,6 +82,7 @@ jobs: yarn setup:github-ci --no-build-ios echo "๐Ÿ— Building Android APP..." export NODE_OPTIONS="--max-old-space-size=8192" + export GRADLE_ARGS="-PciEnv=github --init-script android/github-init.gradle" yarn build:android:qa shell: bash env: @@ -94,19 +95,6 @@ jobs: CI: "true" NODE_OPTIONS: "--max-old-space-size=8192" - GRADLE_OPTS: >- - -Porg.gradle.jvmargs="-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC -XX:G1HeapRegionSize=32m -XX:+UseStringDeduplication -XX:+OptimizeStringConcat" - -Porg.gradle.parallel=true - -Porg.gradle.configureondemand=true - -Porg.gradle.caching=true - -Porg.gradle.daemon=true - -Porg.gradle.workers.max=12 - -Porg.gradle.vfs.watch=true - -Pkotlin.incremental=true - -Pkotlin.incremental.android=true - -Pkotlin.caching.enabled=true - -Porg.gradle.vfs.verbose=false - -Porg.gradle.welcome=NEVER SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} diff --git a/android/github-init.gradle b/android/github-init.gradle new file mode 100644 index 00000000000..bdc3a982bd3 --- /dev/null +++ b/android/github-init.gradle @@ -0,0 +1,54 @@ +// GitHub Actions Init Script + +if (project.hasProperty('ciEnv') && project.property('ciEnv') == 'github') { + + gradle.settingsEvaluated { + // Enable parallel project execution + gradle.startParameter.parallelProjectExecution = true + + // Enable build cache and configuration on demand + gradle.startParameter.isBuildCacheEnabled = true + gradle.startParameter.isConfigurationOnDemand = true + + // Configure daemon and other settings + gradle.startParameter.isDaemon = true + gradle.startParameter.maxWorkerCount = 12 + + // Set JVM args properly via start parameters + gradle.startParameter.jvmArgs += [ + "-Xmx32g", + "-XX:MaxMetaspaceSize=2g", + "-XX:+UseG1GC", + "-XX:G1HeapRegionSize=32m", + "-XX:+UseStringDeduplication", + "-XX:+OptimizeStringConcat" + ] + + // System properties for file system optimizations + System.setProperty('org.gradle.vfs.verbose', 'false') + System.setProperty('org.gradle.welcome', 'NEVER') + } + + allprojects { + // Configure Kotlin incremental compilation properly + tasks.withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompile).configureEach { + kotlinOptions { + // Enable incremental compilation + incremental = true + } + } + + // Enable Kotlin caching if available + afterEvaluate { + if (project.hasProperty('kotlin.incremental')) { + project.setProperty('kotlin.incremental', 'true') + } + if (project.hasProperty('kotlin.incremental.android')) { + project.setProperty('kotlin.incremental.android', 'true') + } + if (project.hasProperty('kotlin.caching.enabled')) { + project.setProperty('kotlin.caching.enabled', 'true') + } + } + } +} diff --git a/scripts/build.sh b/scripts/build.sh index edf729576d8..6e66ff9bdc9 100755 --- a/scripts/build.sh +++ b/scripts/build.sh @@ -527,12 +527,12 @@ buildAndroidQA(){ prebuild_android - # Generate APK - cd android && ./gradlew assembleQaRelease app:assembleQaReleaseAndroidTest -PminSdkVersion=26 -DtestBuildType=release + # Generate APK (with optional GRADLE_ARGS for CI optimizations) + cd android && ./gradlew ${GRADLE_ARGS} assembleQaRelease app:assembleQaReleaseAndroidTest -PminSdkVersion=26 -DtestBuildType=release # GENERATE BUNDLE if [ "$GENERATE_BUNDLE" = true ] ; then - ./gradlew bundleQaRelease + ./gradlew ${GRADLE_ARGS} bundleQaRelease fi if [ "$PRE_RELEASE" = true ] ; then From dfdb84c96d8007398189c5315a322647622aaed9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 15:37:31 +0100 Subject: [PATCH 39/63] path --- .github/workflows/test-android-build-app.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index d559c023c79..578d6322330 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -82,7 +82,7 @@ jobs: yarn setup:github-ci --no-build-ios echo "๐Ÿ— Building Android APP..." export NODE_OPTIONS="--max-old-space-size=8192" - export GRADLE_ARGS="-PciEnv=github --init-script android/github-init.gradle" + export GRADLE_ARGS="-PciEnv=github --init-script github-init.gradle" yarn build:android:qa shell: bash env: From ab10e9fc787b370724090d25aa0733237365862c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 16:07:15 +0100 Subject: [PATCH 40/63] copy gradle --- .github/workflows/test-android-build-app.yml | 4 +- android/github-init.gradle | 54 ------------------- android/gradle.properties.github | 56 ++++++++++++++++++++ scripts/build.sh | 6 +-- 4 files changed, 61 insertions(+), 59 deletions(-) delete mode 100644 android/github-init.gradle create mode 100644 android/gradle.properties.github diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 578d6322330..ac647fa14e4 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -76,13 +76,13 @@ jobs: shell: bash # Run project setup and build the Android QA app (APK and AAB) - - name: Setup Android Environment + - name: Setup and Build Android App run: | echo "๐Ÿš€ Finishing Android Setup..." yarn setup:github-ci --no-build-ios echo "๐Ÿ— Building Android APP..." export NODE_OPTIONS="--max-old-space-size=8192" - export GRADLE_ARGS="-PciEnv=github --init-script github-init.gradle" + cp android/gradle.properties.github android/gradle.properties yarn build:android:qa shell: bash env: diff --git a/android/github-init.gradle b/android/github-init.gradle deleted file mode 100644 index bdc3a982bd3..00000000000 --- a/android/github-init.gradle +++ /dev/null @@ -1,54 +0,0 @@ -// GitHub Actions Init Script - -if (project.hasProperty('ciEnv') && project.property('ciEnv') == 'github') { - - gradle.settingsEvaluated { - // Enable parallel project execution - gradle.startParameter.parallelProjectExecution = true - - // Enable build cache and configuration on demand - gradle.startParameter.isBuildCacheEnabled = true - gradle.startParameter.isConfigurationOnDemand = true - - // Configure daemon and other settings - gradle.startParameter.isDaemon = true - gradle.startParameter.maxWorkerCount = 12 - - // Set JVM args properly via start parameters - gradle.startParameter.jvmArgs += [ - "-Xmx32g", - "-XX:MaxMetaspaceSize=2g", - "-XX:+UseG1GC", - "-XX:G1HeapRegionSize=32m", - "-XX:+UseStringDeduplication", - "-XX:+OptimizeStringConcat" - ] - - // System properties for file system optimizations - System.setProperty('org.gradle.vfs.verbose', 'false') - System.setProperty('org.gradle.welcome', 'NEVER') - } - - allprojects { - // Configure Kotlin incremental compilation properly - tasks.withType(org.jetbrains.kotlin.gradle.tasks.KotlinCompile).configureEach { - kotlinOptions { - // Enable incremental compilation - incremental = true - } - } - - // Enable Kotlin caching if available - afterEvaluate { - if (project.hasProperty('kotlin.incremental')) { - project.setProperty('kotlin.incremental', 'true') - } - if (project.hasProperty('kotlin.incremental.android')) { - project.setProperty('kotlin.incremental.android', 'true') - } - if (project.hasProperty('kotlin.caching.enabled')) { - project.setProperty('kotlin.caching.enabled', 'true') - } - } - } -} diff --git a/android/gradle.properties.github b/android/gradle.properties.github new file mode 100644 index 00000000000..4ab044e5f46 --- /dev/null +++ b/android/gradle.properties.github @@ -0,0 +1,56 @@ +# GitHub Actions-specific Gradle settings +# High-performance settings for 64GB/16CPU runners + +# JVM configuration - high-performance for GitHub Actions +org.gradle.jvmargs=-Xmx32g -XX:MaxMetaspaceSize=2g -XX:+UseG1GC -XX:G1HeapRegionSize=32m -XX:+UseStringDeduplication -XX:+OptimizeStringConcat + +# Enable all performance optimizations for GitHub Actions +org.gradle.parallel=true +org.gradle.configureondemand=true +org.gradle.caching=true +org.gradle.daemon=true +org.gradle.workers.max=12 +org.gradle.vfs.watch=true + +# CI-specific optimizations - enabled for GitHub Actions +kotlin.incremental=true +kotlin.incremental.android=true +kotlin.caching.enabled=true + +# File system optimizations +org.gradle.vfs.verbose=false +org.gradle.welcome=NEVER + +# AndroidX package structure to make it clearer which packages are bundled with the +# Android operating system, and which are packaged with your app's APK +# https://developer.android.com/topic/libraries/support-library/androidx-rn +android.useAndroidX=true +android.enableJetifier=true + +# Enable AAPT2 PNG crunching +android.enablePngCrunchInReleaseBuilds=true + +# TODO: favour arch options here over cli options +# replace them +# Use this property to specify which architecture you want to build. +# You can also override it from the CLI using +# ./gradlew -PreactNativeArchitectures=x86_64 +reactNativeArchitectures=armeabi-v7a,arm64-v8a,x86,x86_64 + +# Use this property to enable support to the new architecture. +# This will allow you to use TurboModules and the Fabric render in +# your application. You should enable this flag either if you want +# to write custom TurboModules/Fabric components OR use libraries that +# are providing them. +newArchEnabled=true + +# Use this property to enable or disable the Hermes JS engine. +# If set to false, you will be using JSC instead. +hermesEnabled=true + +# TODO: explain following config options +# Some of these are depreceated in RN 0.72.15 but when removed the app won't build +android.disableResourceValidation=true + +# Use legacy packaging to compress native libraries in the resulting APK. +expo.useLegacyPackaging=false diff --git a/scripts/build.sh b/scripts/build.sh index 6e66ff9bdc9..edf729576d8 100755 --- a/scripts/build.sh +++ b/scripts/build.sh @@ -527,12 +527,12 @@ buildAndroidQA(){ prebuild_android - # Generate APK (with optional GRADLE_ARGS for CI optimizations) - cd android && ./gradlew ${GRADLE_ARGS} assembleQaRelease app:assembleQaReleaseAndroidTest -PminSdkVersion=26 -DtestBuildType=release + # Generate APK + cd android && ./gradlew assembleQaRelease app:assembleQaReleaseAndroidTest -PminSdkVersion=26 -DtestBuildType=release # GENERATE BUNDLE if [ "$GENERATE_BUNDLE" = true ] ; then - ./gradlew ${GRADLE_ARGS} bundleQaRelease + ./gradlew bundleQaRelease fi if [ "$PRE_RELEASE" = true ] ; then From 0606b450af324545867e3ff67b3b4032f2513501 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Fri, 1 Aug 2025 16:27:41 +0100 Subject: [PATCH 41/63] add gradle cache --- .github/workflows/test-android-build-app.yml | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index ac647fa14e4..33504bed7d8 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -37,6 +37,20 @@ jobs: platform: android setup-simulator: false + # Cache Gradle dependencies (most important for build speed) + - name: Cache Gradle + uses: actions/cache@v4 + with: + path: | + ~/.gradle/caches + ~/.gradle/wrapper + android/.gradle + key: gradle-${{ runner.os }}-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }} + restore-keys: | + gradle-${{ runner.os }}- + + + # Display Android development tools information for debugging - name: Print Android Environment Info run: | @@ -75,6 +89,8 @@ jobs: adb devices || echo "adb devices failed" shell: bash + + # Run project setup and build the Android QA app (APK and AAB) - name: Setup and Build Android App run: | From c47f4907ca12686930dbd098f06015b39b35585a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Sun, 3 Aug 2025 18:06:34 +0100 Subject: [PATCH 42/63] add only one build type --- android/gradle.properties.github | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/android/gradle.properties.github b/android/gradle.properties.github index 4ab044e5f46..8dfc79b3e6e 100644 --- a/android/gradle.properties.github +++ b/android/gradle.properties.github @@ -35,7 +35,7 @@ android.enablePngCrunchInReleaseBuilds=true # Use this property to specify which architecture you want to build. # You can also override it from the CLI using # ./gradlew -PreactNativeArchitectures=x86_64 -reactNativeArchitectures=armeabi-v7a,arm64-v8a,x86,x86_64 +reactNativeArchitectures=arm64-v8a # Use this property to enable support to the new architecture. # This will allow you to use TurboModules and the Fabric render in From 4db514b81dcb5ad667a21c77610a9b45001062c5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 14:49:32 +0100 Subject: [PATCH 43/63] E2e with builds (#17897) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ## **Description** ## **Changelog** CHANGELOG entry: ## **Related issues** Fixes: ## **Manual testing steps** 1. Go to this page... 2. 3. ## **Screenshots/Recordings** ### **Before** ### **After** ## **Pre-merge author checklist** - [ ] Iโ€™ve followed [MetaMask Contributor Docs](https://github.com/MetaMask/contributor-docs) and [MetaMask Mobile Coding Standards](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/CODING_GUIDELINES.md). - [ ] I've completed the PR template to the best of my ability - [ ] Iโ€™ve included tests if applicable - [ ] Iโ€™ve documented my code using [JSDoc](https://jsdoc.app/) format if applicable - [ ] Iโ€™ve applied the right labels on the PR (see [labeling guidelines](https://github.com/MetaMask/metamask-mobile/blob/main/.github/guidelines/LABELING_GUIDELINES.md)). Not required for external contributors. ## **Pre-merge reviewer checklist** - [ ] I've manually tested the PR (e.g. pull and build branch, run the app, test code being changed). - [ ] I confirm that this PR addresses all acceptance criteria described in the ticket it closes and includes the necessary testing evidence such as recordings and or screenshots. --- .detoxrc.js | 18 +- .github/workflows/build-android-e2e.yml | 122 +++++++++ .github/workflows/run-e2e-api-specs.yml | 3 +- .github/workflows/run-e2e-mobile.yml | 238 ------------------ .github/workflows/run-e2e-workflow.yml | 180 +++++++++++++ .../{run-e2e-smoke.yml => run-e2e.yml} | 62 +++-- android/app/build.gradle | 7 +- android/gradle.properties.github | 2 +- e2e/jest.e2e.config.js | 2 +- package.json | 1 + scripts/run-e2e-tags.sh | 10 +- 11 files changed, 370 insertions(+), 275 deletions(-) create mode 100644 .github/workflows/build-android-e2e.yml delete mode 100644 .github/workflows/run-e2e-mobile.yml create mode 100644 .github/workflows/run-e2e-workflow.yml rename .github/workflows/{run-e2e-smoke.yml => run-e2e.yml} (80%) diff --git a/.detoxrc.js b/.detoxrc.js index d95a9e0f1f7..ed6ab7e05e2 100644 --- a/.detoxrc.js +++ b/.detoxrc.js @@ -58,6 +58,10 @@ module.exports = { device: 'android.bitrise.emulator', app: 'android.release', }, + 'android.github_ci.release': { + device: 'android.github_ci.emulator', + app: 'android.release', + }, 'android.emu.flask.release': { device: 'android.bitrise.emulator', app: 'android.flask.release', @@ -71,14 +75,20 @@ module.exports = { }, }, 'android.bitrise.emulator': { + type: 'android.emulator', + device: { + avdName: 'emulator', + } + }, + 'android.github_ci.emulator': { type: 'android.emulator', device: { avdName: 'emulator', }, - // to be used by github action runners later on - // bootArgs: '-skin 1080x2340 -memory 4096 -cores 4 -gpu swiftshader_indirect -no-audio -no-boot-anim -partition-size 4096', - // forceAdbInstall: true, - // gpuMode: 'swiftshader_indirect', + // optimized for GitHub Actions CI runners + bootArgs: '-skin 1080x2340 -memory 6144 -cores 4 -gpu swiftshader_indirect -no-audio -no-boot-anim -partition-size 4096 -no-snapshot-save -no-snapshot-load -cache-size 1024 -accel on -wipe-data -read-only', + forceAdbInstall: true, + gpuMode: 'swiftshader_indirect', }, 'android.emulator': { type: 'android.emulator', diff --git a/.github/workflows/build-android-e2e.yml b/.github/workflows/build-android-e2e.yml new file mode 100644 index 00000000000..f4a703a6baa --- /dev/null +++ b/.github/workflows/build-android-e2e.yml @@ -0,0 +1,122 @@ +# Pure Android E2E build workflow - just builds APKs and uploads artifacts +# No testing, no unnecessary setup - optimized for speed and efficiency + +name: Build Android E2E APKs + +on: + workflow_call: + outputs: + apk-uploaded: + description: 'Whether the APK was successfully uploaded' + value: ${{ jobs.build-android-apks.outputs.apk-uploaded }} + aab-uploaded: + description: 'Whether the AAB was successfully uploaded' + value: ${{ jobs.build-android-apks.outputs.aab-uploaded }} + sourcemap-uploaded: + description: 'Whether the sourcemap was successfully uploaded' + value: ${{ jobs.build-android-apks.outputs.sourcemap-uploaded }} + +jobs: + build-android-apks: + name: Build Android E2E APKs + runs-on: gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl + continue-on-error: true + outputs: + apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} + aab-uploaded: ${{ steps.upload-aab.outcome == 'success' }} + sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} + + steps: + - name: Checkout repo + uses: actions/checkout@v4 + + - name: Setup Android Build Environment + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@self-hosted-runners-config + with: + platform: android + setup-simulator: false + configure-keystores: true + target: qa + + - name: Cache Gradle dependencies + uses: actions/cache@v4 + with: + path: | + ~/.gradle/caches + ~/.gradle/wrapper + android/.gradle + key: gradle-${{ runner.os }}-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }} + restore-keys: | + gradle-${{ runner.os }}- + + - name: Build Android E2E APKs + run: | + echo "๐Ÿš€ Setting up project..." + yarn setup:github-ci --no-build-ios + + echo "๐Ÿ— Building Android E2E APKs..." + export NODE_OPTIONS="--max-old-space-size=8192" + cp android/gradle.properties.github android/gradle.properties + yarn build:android:main:e2e + shell: bash + env: + PLATFORM: android + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + E2E: "true" + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" + NODE_OPTIONS: "--max-old-space-size=8192" + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + + - name: Upload Android APK + id: upload-apk + uses: actions/upload-artifact@v4 + with: + name: app-prod-release.apk + path: android/app/build/outputs/apk/prod/release/app-prod-release.apk + retention-days: 7 + if-no-files-found: error + + - name: Upload Android Test APK + id: upload-test-apk + uses: actions/upload-artifact@v4 + with: + name: app-prod-release-androidTest.apk + path: android/app/build/outputs/apk/androidTest/prod/release/app-prod-release-androidTest.apk + retention-days: 7 + if-no-files-found: error + + - name: Upload Android AAB + id: upload-aab + uses: actions/upload-artifact@v4 + with: + name: app-prod-release.aab + path: android/app/build/outputs/bundle/prodRelease/app-prod-release.aab + retention-days: 7 + if-no-files-found: warn + continue-on-error: true + + - name: Upload Android Source Map + id: upload-sourcemap + uses: actions/upload-artifact@v4 + with: + name: index.android.bundle.map + path: sourcemaps/android/index.android.bundle.map + retention-days: 7 + if-no-files-found: warn + continue-on-error: true diff --git a/.github/workflows/run-e2e-api-specs.yml b/.github/workflows/run-e2e-api-specs.yml index 7a60ca8b1d5..53d0d392389 100644 --- a/.github/workflows/run-e2e-api-specs.yml +++ b/.github/workflows/run-e2e-api-specs.yml @@ -7,13 +7,14 @@ on: workflow_call: workflow_dispatch: pull_request: - types: [labeled] + types: [opened, synchronize] jobs: api-specs-ios: name: "api-specs-ios" if: false runs-on: macos-latest-xlarge + continue-on-error: true env: METAMASK_ENVIRONMENT: 'local' diff --git a/.github/workflows/run-e2e-mobile.yml b/.github/workflows/run-e2e-mobile.yml deleted file mode 100644 index 1f4e14ef252..00000000000 --- a/.github/workflows/run-e2e-mobile.yml +++ /dev/null @@ -1,238 +0,0 @@ -# This workflow runs mobile E2E tests for a specific test category. -# It passes matrix sharding info to the test framework via environment variables. - -name: Test Mobile E2E Category - -on: - workflow_call: - inputs: - test-suite-name: - description: 'Name of the test suite' - required: true - type: string - platform: - description: 'Platform to test (ios or android)' - required: true - type: string - test_suite_tag: - description: 'The Cucumber tag expression to use for filtering tests' - required: true - type: string - use_prebuilt_apps: - description: 'Use pre-built apps from GitHub release instead of building' - required: false - type: boolean - default: true - -jobs: - test-e2e-mobile: - name: ${{ inputs.test-suite-name }} - runs-on: ${{ inputs.platform == 'ios' && 'macos-latest-xlarge' || 'large-mm-test' }} - #runs-on: ${{ inputs.platform == 'ios' && 'macos-latest' || 'ubuntu-latest' }} - - env: - METAMASK_ENVIRONMENT: 'local' - METAMASK_BUILD_TYPE: 'main' - TEST_SUITE_TAG: ${{ inputs.test_suite_tag }} - MM_TEST_WALLET_SRP: ${{ secrets.MM_TEST_WALLET_SRP }} - SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} - SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} - SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} - MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} - MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} - MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} - SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} - MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} - MM_SOLANA_E2E_TEST_SRP: ${{ secrets.MM_SOLANA_E2E_TEST_SRP }} - - steps: - - name: Checkout - uses: actions/checkout@v4 - with: - ref: ${{ github.head_ref || github.ref }} - clean: true - fetch-depth: 0 - - - name: Set up E2E environment - uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - with: - platform: ${{ inputs.platform }} - setup-simulator: ${{ inputs.platform == 'ios' }} - android-avd-name: emulator - android-abi: x86_64 - configure-keystores: false - - - name: Build Detox framework cache (iOS) - if: ${{ inputs.platform == 'ios' }} - run: | - echo "Building Detox framework cache for iOS..." - yarn detox clean-framework-cache - yarn detox build-framework-cache - - #- name: Build E2E app - # if: ${{ !inputs.use_prebuilt_apps }} - # run: | - # platform="${{ inputs.platform }}" - # - # # Set environment variables for build - # export METAMASK_ENVIRONMENT='local' - # export METAMASK_BUILD_TYPE='main' - # export IS_TEST='true' - # export IGNORE_BOXLOGS_DEVELOPMENT="true" - # - # echo "Building E2E app for $platform..." - # - # if [[ "$platform" == "ios" ]]; then - # yarn test:e2e:ios:build:qa-release - # else - # yarn test:e2e:android:build:qa-release - # fi - - - name: Setup pre-built apps from GitHub release - if: ${{ inputs.use_prebuilt_apps }} - run: | - platform="${{ inputs.platform }}" - - echo "๐Ÿš€ Setting up pre-built apps for $platform..." - - # Base URL for artifacts - base_url="https://github.com/MetaMask/tmp-bitrise-migration-artifacts/releases/download/test6" - - # Create required directories - mkdir -p android/app/build/outputs/apk/qa/release/ - mkdir -p ios/build/Build/Products/Release-iphonesimulator/ - - if [[ "$platform" == "ios" ]]; then - echo "๐Ÿ“ฅ Downloading iOS artifacts..." - - # Clean up any existing lock files - find . -name "*.lock" -type f -delete 2>/dev/null || true - - # Download Release-iphonesimulator.zip - if curl -L --fail -o /tmp/Release-iphonesimulator.zip "${base_url}/Release-iphonesimulator.zip"; then - echo "โœ… Downloaded Release-iphonesimulator.zip" - echo "๐Ÿ“ฆ Extracting iOS app..." - - # Extract preserving directory structure (remove -j flag) - cd ios/build/Build/Products/Release-iphonesimulator/ - unzip -o /tmp/Release-iphonesimulator.zip "MetaMask-QA.app/*" - cd - > /dev/null - - # Set proper permissions for the app bundle - chmod -R 755 "ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app/" 2>/dev/null || true - - else - echo "โŒ Failed to download iOS artifacts (Release-iphonesimulator.zip)" - exit 1 - fi - - # Verify iOS setup - if [[ -f "ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app/Info.plist" ]]; then - echo "โœ… iOS app ready for E2E tests" - echo "๐Ÿ“‹ App bundle contents:" - find "ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app/" -maxdepth 1 -exec ls -la {} \; | head -10 - else - echo "โŒ iOS app setup failed - Info.plist not found" - echo "๐Ÿ“‹ Directory contents:" - find "ios/build/Build/Products/Release-iphonesimulator/" -maxdepth 1 -exec ls -la {} \; 2>/dev/null || true - exit 1 - fi - - else - echo "๐Ÿ“ฅ Downloading Android artifacts..." - - if curl -L --fail -o /tmp/outputs.zip "${base_url}/outputs.zip"; then - echo "โœ… Downloaded outputs.zip" - echo "๐Ÿ“ฆ Extracting Android APKs..." - - # Create required directories for both main and test APKs - mkdir -p android/app/build/outputs/apk/androidTest/qa/release/ - - # Extract main APK - unzip -o -j /tmp/outputs.zip "apk/qa/release/app-qa-release.apk" -d "android/app/build/outputs/apk/qa/release/" - - # Extract test APK (androidTest) - unzip -o -j /tmp/outputs.zip "apk/androidTest/qa/release/app-qa-release-androidTest.apk" -d "android/app/build/outputs/apk/androidTest/qa/release/" - - # Verify Android setup - if [[ -f "android/app/build/outputs/apk/qa/release/app-qa-release.apk" ]]; then - echo "โœ… Android main APK ready for E2E tests" - else - echo "โŒ Android main APK setup failed" - exit 1 - fi - - if [[ -f "android/app/build/outputs/apk/androidTest/qa/release/app-qa-release-androidTest.apk" ]]; then - echo "โœ… Android test APK ready for E2E tests" - else - echo "โŒ Android test APK setup failed" - exit 1 - fi - else - echo "โŒ Failed to download Android artifacts (outputs.zip not available)" - exit 1 - fi - fi - - - name: Clean environment before tests (iOS only) - if: ${{ inputs.platform == 'ios' }} - run: | - echo "๐Ÿงน Cleaning iOS environment before E2E tests..." - - # Clean up lock files (iOS-specific issue) - find . -name "*.lock" -type f -delete 2>/dev/null || true - - # Reset iOS simulator - xcrun simctl shutdown all 2>/dev/null || true - xcrun simctl erase all 2>/dev/null || true - - # Clean any hanging processes - pkill -f "Metro\|node\|npm" 2>/dev/null || true - - echo "โœ… iOS environment cleaned" - - - name: Run E2E tests - run: | - platform="${{ inputs.platform }}" - test_suite_tag="${{ inputs.test_suite_tag }}" - - echo "๐Ÿš€ Running ${{ inputs.test-suite-name }} tests on $platform" - - # Validate required test suite tag - if [[ -z "$test_suite_tag" ]]; then - echo "โŒ Error: test_suite_tag is required for non-api-specs tests" - exit 1 - fi - - export TEST_SUITE_TAG="$test_suite_tag" - echo "Using TEST_SUITE_TAG: $TEST_SUITE_TAG" - - # Run tests (Detox/Jest handle retries internally) - echo "๐Ÿš€ Starting E2E tests..." - if [[ "$platform" == "ios" ]]; then - export BITRISE_TRIGGERED_WORKFLOW_ID="ios_workflow" - else - export BITRISE_TRIGGERED_WORKFLOW_ID="android_workflow" - fi - - ./scripts/run-e2e-tags.sh - - echo "โœ… Test execution completed" - - - name: Upload test results - if: always() - uses: actions/upload-artifact@v4 - with: - name: ${{ inputs.test-suite-name }}-test-results - path: e2e/reports/ - retention-days: 7 - - - name: Upload screenshots - if: failure() || cancelled() - uses: actions/upload-artifact@v4 - with: - name: ${{ inputs.test-suite-name }}-screenshots - path: artifacts/ - retention-days: 7 diff --git a/.github/workflows/run-e2e-workflow.yml b/.github/workflows/run-e2e-workflow.yml new file mode 100644 index 00000000000..ed7563a4249 --- /dev/null +++ b/.github/workflows/run-e2e-workflow.yml @@ -0,0 +1,180 @@ +# This workflow runs mobile E2E tests for a specific test category. +# It passes matrix sharding info to the test framework via environment variables. + +name: Test Mobile E2E Category + +on: + workflow_call: + inputs: + test-suite-name: + description: 'Name of the test suite' + required: true + type: string + platform: + description: 'Platform to test (ios or android)' + required: true + type: string + test_suite_tag: + description: 'The Cucumber tag expression to use for filtering tests' + required: true + type: string + + +jobs: + + test-e2e-mobile: + name: ${{ inputs.test-suite-name }} + runs-on: ${{ inputs.platform == 'ios' && 'macos-latest-xlarge' || 'gha-mmsdk-scale-set-ubuntu-22.04-amd64-large' }} + continue-on-error: true + + env: + METAMASK_ENVIRONMENT: 'qa' + METAMASK_BUILD_TYPE: 'main' + TEST_SUITE_TAG: ${{ inputs.test_suite_tag }} + GITHUB_CI: 'true' + MM_TEST_WALLET_SRP: ${{ secrets.MM_TEST_WALLET_SRP }} + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + MM_SOLANA_E2E_TEST_SRP: ${{ secrets.MM_SOLANA_E2E_TEST_SRP }} + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + ref: ${{ github.head_ref || github.ref }} + clean: true + fetch-depth: 0 + + - name: Set up E2E environment + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@self-hosted-runners-config + with: + platform: ${{ inputs.platform }} + setup-simulator: ${{ inputs.platform == 'ios' }} + android-avd-name: emulator + android-abi: x86_64 + configure-keystores: false + + - name: Build Detox framework cache (iOS) + if: ${{ inputs.platform == 'ios' }} + run: | + echo "Building Detox framework cache for iOS..." + yarn detox clean-framework-cache + yarn detox build-framework-cache + + - name: Setup Android artifacts from build job + if: ${{ inputs.platform == 'android' }} + run: | + echo "๐Ÿ— Setting up Android artifacts from build job..." + + # Create required directories + mkdir -p android/app/build/outputs/apk/prod/release/ + + - name: Download Android build artifacts + if: ${{ inputs.platform == 'android' }} + uses: actions/download-artifact@v4 + with: + path: artifacts/ + + - name: Move Android artifacts to expected locations + if: ${{ inputs.platform == 'android' }} + run: | + # Move main APK + if [[ -f "artifacts/app-prod-release.apk/app-prod-release.apk" ]]; then + mkdir -p "android/app/build/outputs/apk/prod/release/" + cp "artifacts/app-prod-release.apk/app-prod-release.apk" "android/app/build/outputs/apk/prod/release/" + echo "โœ… Android main APK ready for E2E tests" + else + echo "โŒ Android main APK not found" + ls -la artifacts/ + exit 1 + fi + + # Move test APK + if [[ -f "artifacts/app-prod-release-androidTest.apk/app-prod-release-androidTest.apk" ]]; then + mkdir -p "android/app/build/outputs/apk/androidTest/prod/release/" + cp "artifacts/app-prod-release-androidTest.apk/app-prod-release-androidTest.apk" "android/app/build/outputs/apk/androidTest/prod/release/" + echo "โœ… Android test APK ready for E2E tests" + else + echo "โŒ Android test APK not found" + ls -la artifacts/ + exit 1 + fi + + - name: Clean environment before tests (iOS only) + if: ${{ inputs.platform == 'ios' }} + run: | + echo "๐Ÿงน Cleaning iOS environment before E2E tests..." + + # Clean up lock files (iOS-specific issue) + find . -name "*.lock" -type f -delete 2>/dev/null || true + + # Reset iOS simulator + xcrun simctl shutdown all 2>/dev/null || true + xcrun simctl erase all 2>/dev/null || true + + # Clean any hanging processes + pkill -f "Metro\|node\|npm" 2>/dev/null || true + + echo "โœ… iOS environment cleaned" + + - name: Run E2E tests + run: | + platform="${{ inputs.platform }}" + test_suite_tag="${{ inputs.test_suite_tag }}" + + echo "๐Ÿš€ Running ${{ inputs.test-suite-name }} tests on $platform" + + # Validate required test suite tag + if [[ -z "$test_suite_tag" ]]; then + echo "โŒ Error: test_suite_tag is required for non-api-specs tests" + exit 1 + fi + + export TEST_SUITE_TAG="$test_suite_tag" + echo "Using TEST_SUITE_TAG: $TEST_SUITE_TAG" + + # Run tests (Detox/Jest handle retries internally) + echo "๐Ÿš€ Starting E2E tests..." + if [[ "$platform" == "ios" ]]; then + export BITRISE_TRIGGERED_WORKFLOW_ID="ios_workflow" + else + export BITRISE_TRIGGERED_WORKFLOW_ID="android_workflow" + fi + + ./scripts/run-e2e-tags.sh + + echo "โœ… Test execution completed" + + - name: Upload test results + if: always() + uses: actions/upload-artifact@v4 + with: + name: ${{ inputs.test-suite-name }}-test-results + path: e2e/reports/ + retention-days: 7 + + - name: Prepare screenshots + if: failure() + run: | + echo "Removing APKs from artifacts..." + find artifacts/ -name "*app-*" -delete 2>/dev/null || true + continue-on-error: true + + - name: Upload screenshots + if: failure() + uses: actions/upload-artifact@v4 + with: + name: ${{ inputs.test-suite-name }}-screenshots + path: artifacts/ + retention-days: 7 diff --git a/.github/workflows/run-e2e-smoke.yml b/.github/workflows/run-e2e.yml similarity index 80% rename from .github/workflows/run-e2e-smoke.yml rename to .github/workflows/run-e2e.yml index 48707603546..1ec0e9b5646 100644 --- a/.github/workflows/run-e2e-smoke.yml +++ b/.github/workflows/run-e2e.yml @@ -7,13 +7,23 @@ on: workflow_call: workflow_dispatch: pull_request: - types: [labeled] + types: [opened, synchronize] + +permissions: + contents: write + id-token: write jobs: + # Build Android APKs once for all Android tests + build-android-apks: + name: "Build Android APKs (Shared)" + uses: ./.github/workflows/build-android-e2e.yml + secrets: inherit + smoke-confirmations-ios: name: "Confirmations Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-confirmations-ios platform: ios @@ -22,8 +32,8 @@ jobs: smoke-confirmations-android: name: "Confirmations Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-confirmations-android platform: android @@ -33,7 +43,7 @@ jobs: smoke-confirmations-redesigned-ios: name: "Confirmations Redesigned Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-confirmations-redesigned-ios platform: ios @@ -43,7 +53,7 @@ jobs: smoke-trade-ios: name: "Trade Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-trade-ios platform: ios @@ -52,8 +62,8 @@ jobs: smoke-trade-android: name: "Trade Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-trade-android platform: android @@ -63,7 +73,7 @@ jobs: smoke-wallet-platform-ios: name: "Wallet Platform Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-wallet-platform-ios platform: ios @@ -72,8 +82,8 @@ jobs: smoke-wallet-platform-android: name: "Wallet Platform Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-wallet-platform-android platform: android @@ -83,7 +93,7 @@ jobs: smoke-identity-ios: name: "Identity Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-identity-ios platform: ios @@ -92,8 +102,8 @@ jobs: smoke-identity-android: name: "Identity Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-identity-android platform: android @@ -103,7 +113,7 @@ jobs: smoke-accounts-ios: name: "Accounts Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-accounts-ios platform: ios @@ -112,8 +122,8 @@ jobs: smoke-accounts-android: name: "Accounts Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-accounts-android platform: android @@ -123,7 +133,7 @@ jobs: smoke-network-abstraction-ios: name: "Network Abstraction Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-network-abstraction-ios platform: ios @@ -132,8 +142,8 @@ jobs: smoke-network-abstraction-android: name: "Network Abstraction Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-network-abstraction-android platform: android @@ -143,7 +153,7 @@ jobs: smoke-network-expansion-ios: name: "Network Expansion Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-network-expansion-ios platform: ios @@ -152,8 +162,8 @@ jobs: smoke-network-expansion-android: name: "Network Expansion Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-network-expansion-android platform: android @@ -163,7 +173,7 @@ jobs: smoke-performance-ios: name: "Performance Smoke (iOS)" if: false - uses: ./.github/workflows/run-e2e-mobile.yml + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-performance-ios platform: ios @@ -172,8 +182,8 @@ jobs: smoke-performance-android: name: "Performance Smoke (Android)" - if: false - uses: ./.github/workflows/run-e2e-mobile.yml + needs: build-android-apks + uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-performance-android platform: android diff --git a/android/app/build.gradle b/android/app/build.gradle index bb5208f3127..5e408a6adce 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -268,7 +268,12 @@ android { prod { dimension "version" applicationId "io.metamask" - signingConfig signingConfigs.release + // Use QA signing config for E2E testing to avoid keystore issues + if (System.getenv("E2E") == 'true') { + signingConfig signingConfigs.qa + } else { + signingConfig signingConfigs.release + } } flask { dimension "version" diff --git a/android/gradle.properties.github b/android/gradle.properties.github index 8dfc79b3e6e..4ab044e5f46 100644 --- a/android/gradle.properties.github +++ b/android/gradle.properties.github @@ -35,7 +35,7 @@ android.enablePngCrunchInReleaseBuilds=true # Use this property to specify which architecture you want to build. # You can also override it from the CLI using # ./gradlew -PreactNativeArchitectures=x86_64 -reactNativeArchitectures=arm64-v8a +reactNativeArchitectures=armeabi-v7a,arm64-v8a,x86,x86_64 # Use this property to enable support to the new architecture. # This will allow you to use TurboModules and the Fabric render in diff --git a/e2e/jest.e2e.config.js b/e2e/jest.e2e.config.js index b3331991f55..53bd3267675 100644 --- a/e2e/jest.e2e.config.js +++ b/e2e/jest.e2e.config.js @@ -2,7 +2,7 @@ require('dotenv').config({ path: '.e2e.env' }); // Determine maxWorkers based on environment -let workers = process.env.CI ? 3 : 1; +const workers = process.env.GITHUB_CI ? 2 : process.env.CI ? 3 : 1; // Set maxWorkers to 1 for performance workflows if (process.env.BITRISE_TRIGGERED_WORKFLOW_ID) { diff --git a/package.json b/package.json index 88c61063395..e4a86415759 100644 --- a/package.json +++ b/package.json @@ -92,6 +92,7 @@ "test:api-specs": "detox reset-lock-file && detox test -c ios.sim.apiSpecs", "test:e2e:ios:main:prod": "IS_TEST='true' NODE_OPTIONS='--experimental-vm-modules' detox test -c ios.sim.main.release", "test:e2e:android:main:prod": "IS_TEST='true' NODE_OPTIONS='--experimental-vm-modules' detox test -c android.emu.release --headless --record-logs all", + "test:e2e:android:run:github:qa-release": "IS_TEST='true' NODE_OPTIONS='--experimental-vm-modules' detox test -c android.github_ci.release --headless --record-logs all", "test:e2e:ios:flask:prod": "IS_TEST='true' NODE_OPTIONS='--experimental-vm-modules' detox test -c ios.sim.flask.release", "test:e2e:android:flask:prod": "IS_TEST='true' NODE_OPTIONS='--experimental-vm-modules' detox test -c android.emu.flask.release --headless --record-logs all", "test:e2e:ios:build:main-release": "IS_TEST='true' detox build -c ios.sim.main.release", diff --git a/scripts/run-e2e-tags.sh b/scripts/run-e2e-tags.sh index a95b29eb67c..baead75c738 100755 --- a/scripts/run-e2e-tags.sh +++ b/scripts/run-e2e-tags.sh @@ -40,9 +40,13 @@ TEST_FILES="${matching_files[*]}" if [[ "$BITRISE_TRIGGERED_WORKFLOW_ID" == *"ios"* ]]; then echo "Detected iOS workflow" IGNORE_BOXLOGS_DEVELOPMENT="true" \ - yarn test:e2e:ios:$METAMASK_BUILD_TYPE:prod $TEST_FILES + yarn test:e2e:ios:run:qa-release $TEST_FILES +elif [[ -n "$GITHUB_CI" ]]; then + echo "Detected GitHub Actions workflow - using GitHub CI configuration" + IGNORE_BOXLOGS_DEVELOPMENT="true" \ + yarn test:e2e:android:run:github:qa-release $TEST_FILES else echo "Detected Android workflow" IGNORE_BOXLOGS_DEVELOPMENT="true" \ - yarn test:e2e:android:$METAMASK_BUILD_TYPE:prod $TEST_FILES -fi \ No newline at end of file + yarn test:e2e:android:run:qa-release $TEST_FILES +fi From 657095f7cc2dabef5bc055a4deec48d06b04ce94 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 14:58:37 +0100 Subject: [PATCH 44/63] update build gradle --- android/app/build.gradle | 37 +++++++++++++++++++------------------ 1 file changed, 19 insertions(+), 18 deletions(-) diff --git a/android/app/build.gradle b/android/app/build.gradle index 8e0ea4d70bd..1d11f89142d 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -317,25 +317,26 @@ android { applicationId "io.metamask" // Use QA signing config for E2E testing to avoid keystore issues if (System.getenv("E2E") == 'true') { - signingConfig signingConfigs.qa + signingConfig signingConfigs.qaProd } else { - signingConfig signingConfigs.release - signingConfig signingConfigs.mainProd - // Use the appropriate signing config based on environment - if (System.getenv("METAMASK_ENVIRONMENT") == 'exp') { - signingConfig signingConfigs.mainExp - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'test') { - signingConfig signingConfigs.mainTest - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'e2e') { - signingConfig signingConfigs.mainE2e - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'prod') { - signingConfig signingConfigs.mainProd - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'rc') { - signingConfig signingConfigs.mainRc - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'beta') { - signingConfig signingConfigs.mainBeta - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'local') { - signingConfig signingConfigs.mainDev + // Use the appropriate signing config based on environment + if (System.getenv("METAMASK_ENVIRONMENT") == 'exp') { + signingConfig signingConfigs.mainExp + } else if (System.getenv("METAMASK_ENVIRONMENT") == 'test') { + signingConfig signingConfigs.mainTest + } else if (System.getenv("METAMASK_ENVIRONMENT") == 'e2e') { + signingConfig signingConfigs.mainE2e + } else if (System.getenv("METAMASK_ENVIRONMENT") == 'prod') { + signingConfig signingConfigs.mainProd + } else if (System.getenv("METAMASK_ENVIRONMENT") == 'rc') { + signingConfig signingConfigs.mainRc + } else if (System.getenv("METAMASK_ENVIRONMENT") == 'beta') { + signingConfig signingConfigs.mainBeta + } else if (System.getenv("METAMASK_ENVIRONMENT") == 'local') { + signingConfig signingConfigs.mainDev + } else { + signingConfig signingConfigs.mainProd + } } } flask { From 6bd97380cd0a5aa5a8df8a4d5e5b12bee505fc95 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 15:05:05 +0100 Subject: [PATCH 45/63] typos --- android/app/build.gradle | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/android/app/build.gradle b/android/app/build.gradle index 1d11f89142d..919c972bb81 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -304,8 +304,8 @@ android { } } - flavorDimensions "version" - productFlavors { + flavorDimensions "version" + productFlavors { qa { dimension "version" applicationIdSuffix ".qa" @@ -354,7 +354,7 @@ android { signingConfig signingConfigs.flaskDev } } - } + } buildTypes.each { it.buildConfigField 'String', 'foxCode', "\"$System.env.MM_FOX_CODE\"" From 5fb546ca7f9ab28ea1e520c2011d9e5141f7ee39 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 15:10:38 +0100 Subject: [PATCH 46/63] run tests only if build passes --- .github/workflows/build-android-e2e.yml | 1 - .github/workflows/run-e2e.yml | 8 +++++++ android/app/build.gradle | 28 ++++++++++++------------- 3 files changed, 22 insertions(+), 15 deletions(-) diff --git a/.github/workflows/build-android-e2e.yml b/.github/workflows/build-android-e2e.yml index f4a703a6baa..8814466199e 100644 --- a/.github/workflows/build-android-e2e.yml +++ b/.github/workflows/build-android-e2e.yml @@ -20,7 +20,6 @@ jobs: build-android-apks: name: Build Android E2E APKs runs-on: gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl - continue-on-error: true outputs: apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} aab-uploaded: ${{ steps.upload-aab.outcome == 'success' }} diff --git a/.github/workflows/run-e2e.yml b/.github/workflows/run-e2e.yml index 1ec0e9b5646..b30a3840fa1 100644 --- a/.github/workflows/run-e2e.yml +++ b/.github/workflows/run-e2e.yml @@ -33,6 +33,7 @@ jobs: smoke-confirmations-android: name: "Confirmations Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-confirmations-android @@ -63,6 +64,7 @@ jobs: smoke-trade-android: name: "Trade Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-trade-android @@ -83,6 +85,7 @@ jobs: smoke-wallet-platform-android: name: "Wallet Platform Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-wallet-platform-android @@ -103,6 +106,7 @@ jobs: smoke-identity-android: name: "Identity Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-identity-android @@ -123,6 +127,7 @@ jobs: smoke-accounts-android: name: "Accounts Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-accounts-android @@ -143,6 +148,7 @@ jobs: smoke-network-abstraction-android: name: "Network Abstraction Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-network-abstraction-android @@ -163,6 +169,7 @@ jobs: smoke-network-expansion-android: name: "Network Expansion Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-network-expansion-android @@ -183,6 +190,7 @@ jobs: smoke-performance-android: name: "Performance Smoke (Android)" needs: build-android-apks + if: always() && needs.build-android-apks.result != 'failure' uses: ./.github/workflows/run-e2e-workflow.yml with: test-suite-name: smoke-performance-android diff --git a/android/app/build.gradle b/android/app/build.gradle index 919c972bb81..aae71e21840 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -315,28 +315,28 @@ android { prod { dimension "version" applicationId "io.metamask" - // Use QA signing config for E2E testing to avoid keystore issues - if (System.getenv("E2E") == 'true') { - signingConfig signingConfigs.qaProd - } else { - // Use the appropriate signing config based on environment - if (System.getenv("METAMASK_ENVIRONMENT") == 'exp') { + // Use appropriate signing config based on environment + def env = System.getenv("METAMASK_ENVIRONMENT") + def isE2E = System.getenv("E2E") + + if (isE2E) { + signingConfig signingConfigs.qaProd + } else if (env == 'exp') { signingConfig signingConfigs.mainExp - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'test') { + } else if (env == 'test') { signingConfig signingConfigs.mainTest - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'e2e') { + } else if (env == 'e2e') { signingConfig signingConfigs.mainE2e - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'prod') { + } else if (env == 'prod') { signingConfig signingConfigs.mainProd - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'rc') { + } else if (env == 'rc') { signingConfig signingConfigs.mainRc - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'beta') { + } else if (env == 'beta') { signingConfig signingConfigs.mainBeta - } else if (System.getenv("METAMASK_ENVIRONMENT") == 'local') { + } else if (env == 'local') { signingConfig signingConfigs.mainDev - } else { + } else { signingConfig signingConfigs.mainProd - } } } flask { From 4d12e33f407cb20f08d28a79e75c1cc9deaf1059 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 16:12:31 +0100 Subject: [PATCH 47/63] variable reassign --- e2e/jest.e2e.config.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/e2e/jest.e2e.config.js b/e2e/jest.e2e.config.js index 53bd3267675..ad314171de1 100644 --- a/e2e/jest.e2e.config.js +++ b/e2e/jest.e2e.config.js @@ -2,7 +2,7 @@ require('dotenv').config({ path: '.e2e.env' }); // Determine maxWorkers based on environment -const workers = process.env.GITHUB_CI ? 2 : process.env.CI ? 3 : 1; +let workers = process.env.GITHUB_CI ? 2 : process.env.CI ? 3 : 1; // Set maxWorkers to 1 for performance workflows if (process.env.BITRISE_TRIGGERED_WORKFLOW_ID) { From 37cca1098912d3e10d51c290d515f3ac9697eb18 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 16:20:43 +0100 Subject: [PATCH 48/63] defensive check --- scripts/build.sh | 1 + 1 file changed, 1 insertion(+) diff --git a/scripts/build.sh b/scripts/build.sh index 4cb575bcb2a..a0e78e142c0 100755 --- a/scripts/build.sh +++ b/scripts/build.sh @@ -22,6 +22,7 @@ echo "ENVIRONMENT = $ENVIRONMENT" export SENTRY_DISABLE_AUTO_UPLOAD=${SENTRY_DISABLE_AUTO_UPLOAD:-"true"} export METAMASK_BUILD_TYPE=${MODE:-"$METAMASK_BUILD_TYPE"} export METAMASK_ENVIRONMENT=${ENVIRONMENT:-"$METAMASK_ENVIRONMENT"} +export GITHUB_CI=${GITHUB_CI:-"false"} export EXPO_NO_TYPESCRIPT_SETUP=1 envFileMissing() { From 8a4f905ad3a32b9dc4a7df2d3edf2960a19d8228 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 16:27:37 +0100 Subject: [PATCH 49/63] no more test build --- .github/workflows/test-android-build-app.yml | 179 ------------------- 1 file changed, 179 deletions(-) delete mode 100644 .github/workflows/test-android-build-app.yml diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml deleted file mode 100644 index 33504bed7d8..00000000000 --- a/.github/workflows/test-android-build-app.yml +++ /dev/null @@ -1,179 +0,0 @@ -name: Test Android Build QA App - -on: - push: - workflow_dispatch: - inputs: - retention_days: - description: 'Number of days to retain artifacts' - required: false - default: '7' - type: string - -permissions: - contents: write - id-token: write - -jobs: - android-build: - name: Test Android Build QA App - #runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large - runs-on: gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl - outputs: - artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} - apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} - aab-uploaded: ${{ steps.upload-aab.outcome == 'success' }} - sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} - steps: - # Get the source code from the repository - - name: Checkout repo - uses: actions/checkout@v4 - - # Install Android SDK, Node.js, and other Android development dependencies - - name: Installing Android Environment Setup - # uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - uses: MetaMask/github-tools/.github/actions/setup-e2e-env@self-hosted-runners-config - with: - platform: android - setup-simulator: false - - # Cache Gradle dependencies (most important for build speed) - - name: Cache Gradle - uses: actions/cache@v4 - with: - path: | - ~/.gradle/caches - ~/.gradle/wrapper - android/.gradle - key: gradle-${{ runner.os }}-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }} - restore-keys: | - gradle-${{ runner.os }}- - - - - # Display Android development tools information for debugging - - name: Print Android Environment Info - run: | - echo "๐Ÿ”ง Node.js Version:" - node -v || echo "Node not found" - echo "Android Studio Version:" - /Applications/Android\ Studio.app/Contents/MacOS/studio --version || echo "Check manually via finder" - echo "๐Ÿงถ Yarn Version:" - yarn -v || echo "Yarn not found" - echo "๐Ÿ“ฆ SDK Manager Version:" - sdkmanager --version || echo "sdkmanager not found" - echo "๐Ÿ“ฑ ADB Version:" - adb version || echo "adb not found" - echo "๐Ÿ–ฅ๏ธ Emulator Version:" - emulator -version || echo "emulator not found" - echo "๐Ÿงฑ NDK Info:" - echo "NDK Dir: $ANDROID_SDK_ROOT/ndk/${NDK_VERSION:-unknown}" - if [ -n "${NDK_VERSION}" ] && [ -f "$ANDROID_SDK_ROOT/ndk/${NDK_VERSION}/source.properties" ]; then - grep "Pkg.Revision" "$ANDROID_SDK_ROOT/ndk/${NDK_VERSION}/source.properties" || echo "NDK version info not found" - else - echo "NDK not found or NDK_VERSION not set" - fi - echo "๐Ÿ”ง Checking for ndk-build:" - command -v ndk-build || echo "ndk-build not found in PATH" - echo "๐Ÿ”ง Checking for clang:" - command -v clang || echo "clang not found in PATH" - echo "๐Ÿ”ง Checking for llvm-ar:" - command -v llvm-ar || echo "llvm-ar not found in PATH" - echo "๐Ÿ“ฑ Available AVD Devices:" - avdmanager list device || echo "avdmanager not found" - echo "๐Ÿ“ฑ Available System Images:" - sdkmanager --list | grep "system-images;" || echo "No system images listed" - echo "๐ŸŸข Emulator Processes:" - pgrep -fl emulator || echo "No running emulator processes" - echo "๐Ÿ“ฑ Connected Android Devices:" - adb devices || echo "adb devices failed" - shell: bash - - - - # Run project setup and build the Android QA app (APK and AAB) - - name: Setup and Build Android App - run: | - echo "๐Ÿš€ Finishing Android Setup..." - yarn setup:github-ci --no-build-ios - echo "๐Ÿ— Building Android APP..." - export NODE_OPTIONS="--max-old-space-size=8192" - cp android/gradle.properties.github android/gradle.properties - yarn build:android:qa - shell: bash - env: - PLATFORM: android - METAMASK_ENVIRONMENT: qa - METAMASK_BUILD_TYPE: main - IS_TEST: true - IGNORE_BOXLOGS_DEVELOPMENT: true - GITHUB_CI: "true" - CI: "true" - - NODE_OPTIONS: "--max-old-space-size=8192" - - SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} - SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} - SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} - SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} - - MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} - MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} - - MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} - MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} - MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} - GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} - GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} - - # Upload the Android APK file for device installation and testing - - name: Upload Android APK Artifact - id: upload-apk - uses: actions/upload-artifact@v4 - with: - name: app-qa-release.apk - path: android/app/build/outputs/apk/qa/release/app-qa-release.apk - retention-days: ${{ inputs.retention_days }} - if-no-files-found: error - continue-on-error: true - - # Upload the Android App Bundle (AAB) for Play Store distribution - - name: Upload Android AAB Artifact - id: upload-aab - uses: actions/upload-artifact@v4 - with: - name: app-qa-release.aab - path: android/app/build/outputs/bundle/qaRelease/app-qa-release.aab - retention-days: ${{ inputs.retention_days }} - if-no-files-found: warn - continue-on-error: true - - # Upload source map file for crash debugging and error tracking - - name: Upload Android Source Map - id: upload-sourcemap - uses: actions/upload-artifact@v4 - with: - name: index.android.bundle.map - path: sourcemaps/android/index.android.bundle.map - retention-days: ${{ inputs.retention_days }} - if-no-files-found: warn - continue-on-error: true - - # Generate artifact download URL and display upload status summary - - name: Set Artifacts URL and Status - id: set-artifacts-url - run: | - ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" - echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" - echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" - echo "" - echo "Upload Status Summary:" - echo "- ๐Ÿค– APK: ${{ steps.upload-apk.outcome }}" - echo "- ๐Ÿ“ฆ AAB Bundle: ${{ steps.upload-aab.outcome }}" - echo "- ๐Ÿ“ฆ Source Map: ${{ steps.upload-sourcemap.outcome }}" - - env: - GITHUB_REPOSITORY: "${{ github.repository }}" - GITHUB_RUN_ID: "${{ github.run_id }}" From ab46324a459ef7e6cda7912a240ecbcd62844244 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 16:29:54 +0100 Subject: [PATCH 50/63] run e2e fix --- scripts/run-e2e-tags.sh | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/scripts/run-e2e-tags.sh b/scripts/run-e2e-tags.sh index baead75c738..b10d4af5705 100755 --- a/scripts/run-e2e-tags.sh +++ b/scripts/run-e2e-tags.sh @@ -40,7 +40,7 @@ TEST_FILES="${matching_files[*]}" if [[ "$BITRISE_TRIGGERED_WORKFLOW_ID" == *"ios"* ]]; then echo "Detected iOS workflow" IGNORE_BOXLOGS_DEVELOPMENT="true" \ - yarn test:e2e:ios:run:qa-release $TEST_FILES + yarn test:e2e:ios:$METAMASK_BUILD_TYPE:prod $TEST_FILES elif [[ -n "$GITHUB_CI" ]]; then echo "Detected GitHub Actions workflow - using GitHub CI configuration" IGNORE_BOXLOGS_DEVELOPMENT="true" \ @@ -48,5 +48,5 @@ elif [[ -n "$GITHUB_CI" ]]; then else echo "Detected Android workflow" IGNORE_BOXLOGS_DEVELOPMENT="true" \ - yarn test:e2e:android:run:qa-release $TEST_FILES + yarn test:e2e:android:$METAMASK_BUILD_TYPE:prod $TEST_FILES fi From 640bc08328f253f3720de5a2ee4d239ed4a10e5a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 16:46:02 +0100 Subject: [PATCH 51/63] comment ios --- .github/workflows/test-ios-build-app.yml | 340 +++++++++++------------ 1 file changed, 170 insertions(+), 170 deletions(-) diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 5484715b6f4..9472b8c3a08 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -1,170 +1,170 @@ -name: Test iOS Build QA App - -on: -# push: - workflow_dispatch: - inputs: - retention_days: - description: 'Number of days to retain the uploaded artifacts' - required: false - default: '7' - type: string - -permissions: - contents: write - id-token: write - -jobs: - ios-build: - name: Test iOS QA Build App - runs-on: macos-15 - outputs: - artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} - app-uploaded: ${{ steps.upload-app.outcome == 'success' }} - ipa-uploaded: ${{ steps.upload-ipa.outcome == 'success' }} - archive-uploaded: ${{ steps.upload-archive.outcome == 'success' }} - sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} - env: - GITHUB_CI: "true" # โœ… This ensures it's available during pod install - steps: - # Get the source code from the repository - - name: Checkout repo - uses: actions/checkout@v4 - - # Display system information for debugging purposes - - name: Detect CPU architecture - run: | - echo "Arch: $(uname -m)" - if [[ "$(uname -m)" == "x86_64" ]]; then - echo "Detected Intel runner" - else - echo "Detected Apple Silicon runner" - fi - - - name: Print system resources - run: | - echo "๐Ÿง  Memory info:" - vm_stat - echo "" - echo "๐Ÿ’ป CPU info:" - sysctl -n hw.ncpu - sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' - shell: bash - - # Install Node.js, Xcode tools, and other iOS development dependencies - - name: Installing iOS Environment Setup - uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions - with: - platform: ios - setup-simulator: false - - - name: Print iOS tool versions - run: | - echo "๐Ÿ”ง Node.js Version:" - node -v || echo "Node not found" - echo "๐Ÿงถ Yarn Version:" - yarn -v || echo "Yarn not found" - echo "๐Ÿ“ฆ CocoaPods Version:" - pod --version || echo "CocoaPods not found" - echo "๐Ÿ› ๏ธ Xcode Path:" - xcode-select -p || echo "Xcode not found" - echo "๐Ÿ“ฑ Booted iOS Simulators:" - xcrun simctl list | grep Booted || echo "No booted simulators found" - shell: bash - - # Run project setup and build the iOS QA app for simulator - - name: Setup iOS Environment - run: | - echo "๐Ÿš€ Finishing iOS Setup..." - yarn setup:github-ci --build-ios --no-build-android - echo "๐Ÿ— Building iOS APP..." - yarn build:ios:qa - shell: bash - env: - PLATFORM: ios - METAMASK_ENVIRONMENT: qa - METAMASK_BUILD_TYPE: main - IS_TEST: true - IGNORE_BOXLOGS_DEVELOPMENT: true - GITHUB_CI: "true" - CI: "true" - - NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners - - SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} - SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} - SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} - SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} - - MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} - MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} - - MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} - MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} - MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} - MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} - GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} - GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} - - # Upload the iOS .app file that works in simulators (no certificates needed) - - name: Upload iOS APP Artifact (Simulator) - id: upload-app - uses: actions/upload-artifact@v4 - with: - name: MetaMask-QA.app - path: ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app - retention-days: ${{ inputs.retention_days }} - if-no-files-found: error - continue-on-error: true - - # Upload iOS .ipa file for device installation (requires certificates - may not exist) - - name: Upload iOS IPA Artifact (Device) - id: upload-ipa - uses: actions/upload-artifact@v4 - with: - name: MetaMask-QA.ipa - path: ios/build/output/MetaMask-QA.ipa - retention-days: ${{ inputs.retention_days }} - if-no-files-found: error - continue-on-error: true - - # Upload iOS .xcarchive file for debugging and re-signing (requires certificates - may not exist) - - name: Upload iOS Archive Artifact - id: upload-archive - uses: actions/upload-artifact@v4 - with: - name: MetaMask-QA.xcarchive - path: ios/build/MetaMask-QA.xcarchive - retention-days: ${{ inputs.retention_days }} - if-no-files-found: error - continue-on-error: true - - # Upload source map file for crash debugging and error tracking if exists - - name: Upload iOS Source Map - id: upload-sourcemap - uses: actions/upload-artifact@v4 - with: - name: index.js.map - path: sourcemaps/ios/index.js.map - retention-days: ${{ inputs.retention_days }} - if-no-files-found: error - continue-on-error: true - - # Generate artifact download URL and display upload status summary - - name: Set Artifacts URL and Status - id: set-artifacts-url - run: | - ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" - echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" - echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" - echo "" - echo "Upload Status Summary:" - echo "- ๏ฃฟ APP (Simulator): ${{ steps.upload-app.outcome }}" - echo "- ๏ฃฟ IPA (Device): ${{ steps.upload-ipa.outcome }}" - echo "- ๏ฃฟ Archive: ${{ steps.upload-archive.outcome }}" - echo "- ๏ฃฟ Source Map: ${{ steps.upload-sourcemap.outcome }}" - - env: - GITHUB_REPOSITORY: "${{ github.repository }}" - GITHUB_RUN_ID: "${{ github.run_id }}" \ No newline at end of file +# name: Test iOS Build QA App + +# on: +# # push: +# workflow_dispatch: +# inputs: +# retention_days: +# description: 'Number of days to retain the uploaded artifacts' +# required: false +# default: '7' +# type: string + +# permissions: +# contents: write +# id-token: write + +# jobs: +# ios-build: +# name: Test iOS QA Build App +# runs-on: macos-15 +# outputs: +# artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} +# app-uploaded: ${{ steps.upload-app.outcome == 'success' }} +# ipa-uploaded: ${{ steps.upload-ipa.outcome == 'success' }} +# archive-uploaded: ${{ steps.upload-archive.outcome == 'success' }} +# sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} +# env: +# GITHUB_CI: "true" # โœ… This ensures it's available during pod install +# steps: +# # Get the source code from the repository +# - name: Checkout repo +# uses: actions/checkout@v4 + +# # Display system information for debugging purposes +# - name: Detect CPU architecture +# run: | +# echo "Arch: $(uname -m)" +# if [[ "$(uname -m)" == "x86_64" ]]; then +# echo "Detected Intel runner" +# else +# echo "Detected Apple Silicon runner" +# fi + +# - name: Print system resources +# run: | +# echo "๐Ÿง  Memory info:" +# vm_stat +# echo "" +# echo "๐Ÿ’ป CPU info:" +# sysctl -n hw.ncpu +# sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' +# shell: bash + +# # Install Node.js, Xcode tools, and other iOS development dependencies +# - name: Installing iOS Environment Setup +# uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions +# with: +# platform: ios +# setup-simulator: false + +# - name: Print iOS tool versions +# run: | +# echo "๐Ÿ”ง Node.js Version:" +# node -v || echo "Node not found" +# echo "๐Ÿงถ Yarn Version:" +# yarn -v || echo "Yarn not found" +# echo "๐Ÿ“ฆ CocoaPods Version:" +# pod --version || echo "CocoaPods not found" +# echo "๐Ÿ› ๏ธ Xcode Path:" +# xcode-select -p || echo "Xcode not found" +# echo "๐Ÿ“ฑ Booted iOS Simulators:" +# xcrun simctl list | grep Booted || echo "No booted simulators found" +# shell: bash + +# # Run project setup and build the iOS QA app for simulator +# - name: Setup iOS Environment +# run: | +# echo "๐Ÿš€ Finishing iOS Setup..." +# yarn setup:github-ci --build-ios --no-build-android +# echo "๐Ÿ— Building iOS APP..." +# yarn build:ios:qa +# shell: bash +# env: +# PLATFORM: ios +# METAMASK_ENVIRONMENT: qa +# METAMASK_BUILD_TYPE: main +# IS_TEST: true +# IGNORE_BOXLOGS_DEVELOPMENT: true +# GITHUB_CI: "true" +# CI: "true" + +# NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners + +# SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} +# SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} +# SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} +# SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + +# MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} +# MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + +# MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} +# MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} +# MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} +# MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} +# MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} +# GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} +# GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + +# # Upload the iOS .app file that works in simulators (no certificates needed) +# - name: Upload iOS APP Artifact (Simulator) +# id: upload-app +# uses: actions/upload-artifact@v4 +# with: +# name: MetaMask-QA.app +# path: ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app +# retention-days: ${{ inputs.retention_days }} +# if-no-files-found: error +# continue-on-error: true + +# # Upload iOS .ipa file for device installation (requires certificates - may not exist) +# - name: Upload iOS IPA Artifact (Device) +# id: upload-ipa +# uses: actions/upload-artifact@v4 +# with: +# name: MetaMask-QA.ipa +# path: ios/build/output/MetaMask-QA.ipa +# retention-days: ${{ inputs.retention_days }} +# if-no-files-found: error +# continue-on-error: true + +# # Upload iOS .xcarchive file for debugging and re-signing (requires certificates - may not exist) +# - name: Upload iOS Archive Artifact +# id: upload-archive +# uses: actions/upload-artifact@v4 +# with: +# name: MetaMask-QA.xcarchive +# path: ios/build/MetaMask-QA.xcarchive +# retention-days: ${{ inputs.retention_days }} +# if-no-files-found: error +# continue-on-error: true + +# # Upload source map file for crash debugging and error tracking if exists +# - name: Upload iOS Source Map +# id: upload-sourcemap +# uses: actions/upload-artifact@v4 +# with: +# name: index.js.map +# path: sourcemaps/ios/index.js.map +# retention-days: ${{ inputs.retention_days }} +# if-no-files-found: error +# continue-on-error: true + +# # Generate artifact download URL and display upload status summary +# - name: Set Artifacts URL and Status +# id: set-artifacts-url +# run: | +# ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" +# echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" +# echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" +# echo "" +# echo "Upload Status Summary:" +# echo "- APP (Simulator): ${{ steps.upload-app.outcome }}" +# echo "- IPA (Device): ${{ steps.upload-ipa.outcome }}" +# echo "- Archive: ${{ steps.upload-archive.outcome }}" +# echo "- Source Map: ${{ steps.upload-sourcemap.outcome }}" + +# env: +# GITHUB_REPOSITORY: "${{ github.repository }}" +# GITHUB_RUN_ID: "${{ github.run_id }}" From 44a60e08d8391df8ad746ff6f7849aea5ec3939f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 16:56:54 +0100 Subject: [PATCH 52/63] Revert "no more test build" This reverts commit 8a4f905ad3a32b9dc4a7df2d3edf2960a19d8228. --- .github/workflows/test-android-build-app.yml | 179 +++++++++++++++++++ 1 file changed, 179 insertions(+) create mode 100644 .github/workflows/test-android-build-app.yml diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml new file mode 100644 index 00000000000..33504bed7d8 --- /dev/null +++ b/.github/workflows/test-android-build-app.yml @@ -0,0 +1,179 @@ +name: Test Android Build QA App + +on: + push: + workflow_dispatch: + inputs: + retention_days: + description: 'Number of days to retain artifacts' + required: false + default: '7' + type: string + +permissions: + contents: write + id-token: write + +jobs: + android-build: + name: Test Android Build QA App + #runs-on: gha-mm-scale-set-ubuntu-22.04-amd64-large + runs-on: gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl + outputs: + artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} + apk-uploaded: ${{ steps.upload-apk.outcome == 'success' }} + aab-uploaded: ${{ steps.upload-aab.outcome == 'success' }} + sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} + steps: + # Get the source code from the repository + - name: Checkout repo + uses: actions/checkout@v4 + + # Install Android SDK, Node.js, and other Android development dependencies + - name: Installing Android Environment Setup + # uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@self-hosted-runners-config + with: + platform: android + setup-simulator: false + + # Cache Gradle dependencies (most important for build speed) + - name: Cache Gradle + uses: actions/cache@v4 + with: + path: | + ~/.gradle/caches + ~/.gradle/wrapper + android/.gradle + key: gradle-${{ runner.os }}-${{ hashFiles('**/*.gradle*', '**/gradle-wrapper.properties') }} + restore-keys: | + gradle-${{ runner.os }}- + + + + # Display Android development tools information for debugging + - name: Print Android Environment Info + run: | + echo "๐Ÿ”ง Node.js Version:" + node -v || echo "Node not found" + echo "Android Studio Version:" + /Applications/Android\ Studio.app/Contents/MacOS/studio --version || echo "Check manually via finder" + echo "๐Ÿงถ Yarn Version:" + yarn -v || echo "Yarn not found" + echo "๐Ÿ“ฆ SDK Manager Version:" + sdkmanager --version || echo "sdkmanager not found" + echo "๐Ÿ“ฑ ADB Version:" + adb version || echo "adb not found" + echo "๐Ÿ–ฅ๏ธ Emulator Version:" + emulator -version || echo "emulator not found" + echo "๐Ÿงฑ NDK Info:" + echo "NDK Dir: $ANDROID_SDK_ROOT/ndk/${NDK_VERSION:-unknown}" + if [ -n "${NDK_VERSION}" ] && [ -f "$ANDROID_SDK_ROOT/ndk/${NDK_VERSION}/source.properties" ]; then + grep "Pkg.Revision" "$ANDROID_SDK_ROOT/ndk/${NDK_VERSION}/source.properties" || echo "NDK version info not found" + else + echo "NDK not found or NDK_VERSION not set" + fi + echo "๐Ÿ”ง Checking for ndk-build:" + command -v ndk-build || echo "ndk-build not found in PATH" + echo "๐Ÿ”ง Checking for clang:" + command -v clang || echo "clang not found in PATH" + echo "๐Ÿ”ง Checking for llvm-ar:" + command -v llvm-ar || echo "llvm-ar not found in PATH" + echo "๐Ÿ“ฑ Available AVD Devices:" + avdmanager list device || echo "avdmanager not found" + echo "๐Ÿ“ฑ Available System Images:" + sdkmanager --list | grep "system-images;" || echo "No system images listed" + echo "๐ŸŸข Emulator Processes:" + pgrep -fl emulator || echo "No running emulator processes" + echo "๐Ÿ“ฑ Connected Android Devices:" + adb devices || echo "adb devices failed" + shell: bash + + + + # Run project setup and build the Android QA app (APK and AAB) + - name: Setup and Build Android App + run: | + echo "๐Ÿš€ Finishing Android Setup..." + yarn setup:github-ci --no-build-ios + echo "๐Ÿ— Building Android APP..." + export NODE_OPTIONS="--max-old-space-size=8192" + cp android/gradle.properties.github android/gradle.properties + yarn build:android:qa + shell: bash + env: + PLATFORM: android + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" + + NODE_OPTIONS: "--max-old-space-size=8192" + + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + + # Upload the Android APK file for device installation and testing + - name: Upload Android APK Artifact + id: upload-apk + uses: actions/upload-artifact@v4 + with: + name: app-qa-release.apk + path: android/app/build/outputs/apk/qa/release/app-qa-release.apk + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error + continue-on-error: true + + # Upload the Android App Bundle (AAB) for Play Store distribution + - name: Upload Android AAB Artifact + id: upload-aab + uses: actions/upload-artifact@v4 + with: + name: app-qa-release.aab + path: android/app/build/outputs/bundle/qaRelease/app-qa-release.aab + retention-days: ${{ inputs.retention_days }} + if-no-files-found: warn + continue-on-error: true + + # Upload source map file for crash debugging and error tracking + - name: Upload Android Source Map + id: upload-sourcemap + uses: actions/upload-artifact@v4 + with: + name: index.android.bundle.map + path: sourcemaps/android/index.android.bundle.map + retention-days: ${{ inputs.retention_days }} + if-no-files-found: warn + continue-on-error: true + + # Generate artifact download URL and display upload status summary + - name: Set Artifacts URL and Status + id: set-artifacts-url + run: | + ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" + echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" + echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" + echo "" + echo "Upload Status Summary:" + echo "- ๐Ÿค– APK: ${{ steps.upload-apk.outcome }}" + echo "- ๐Ÿ“ฆ AAB Bundle: ${{ steps.upload-aab.outcome }}" + echo "- ๐Ÿ“ฆ Source Map: ${{ steps.upload-sourcemap.outcome }}" + + env: + GITHUB_REPOSITORY: "${{ github.repository }}" + GITHUB_RUN_ID: "${{ github.run_id }}" From 1ce7a5b99c5aa866fe9eeb1936f9c3e36a08a240 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Wed, 6 Aug 2025 17:00:15 +0100 Subject: [PATCH 53/63] remove auto push --- .github/workflows/test-android-build-app.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.github/workflows/test-android-build-app.yml b/.github/workflows/test-android-build-app.yml index 33504bed7d8..dd7749d1ddf 100644 --- a/.github/workflows/test-android-build-app.yml +++ b/.github/workflows/test-android-build-app.yml @@ -1,7 +1,6 @@ name: Test Android Build QA App on: - push: workflow_dispatch: inputs: retention_days: From 68855bbb742de25b44dcfb4b338f494c352d5d19 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 09:07:09 +0100 Subject: [PATCH 54/63] correct file --- scripts/build.sh | 1 - scripts/run-e2e-tags.sh | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/scripts/build.sh b/scripts/build.sh index a0e78e142c0..4cb575bcb2a 100755 --- a/scripts/build.sh +++ b/scripts/build.sh @@ -22,7 +22,6 @@ echo "ENVIRONMENT = $ENVIRONMENT" export SENTRY_DISABLE_AUTO_UPLOAD=${SENTRY_DISABLE_AUTO_UPLOAD:-"true"} export METAMASK_BUILD_TYPE=${MODE:-"$METAMASK_BUILD_TYPE"} export METAMASK_ENVIRONMENT=${ENVIRONMENT:-"$METAMASK_ENVIRONMENT"} -export GITHUB_CI=${GITHUB_CI:-"false"} export EXPO_NO_TYPESCRIPT_SETUP=1 envFileMissing() { diff --git a/scripts/run-e2e-tags.sh b/scripts/run-e2e-tags.sh index b10d4af5705..a1459ac1ee6 100755 --- a/scripts/run-e2e-tags.sh +++ b/scripts/run-e2e-tags.sh @@ -41,7 +41,7 @@ if [[ "$BITRISE_TRIGGERED_WORKFLOW_ID" == *"ios"* ]]; then echo "Detected iOS workflow" IGNORE_BOXLOGS_DEVELOPMENT="true" \ yarn test:e2e:ios:$METAMASK_BUILD_TYPE:prod $TEST_FILES -elif [[ -n "$GITHUB_CI" ]]; then +elif [[ -n "${GITHUB_CI:-}" ]]; then echo "Detected GitHub Actions workflow - using GitHub CI configuration" IGNORE_BOXLOGS_DEVELOPMENT="true" \ yarn test:e2e:android:run:github:qa-release $TEST_FILES From 8dc850534a85412b1cfe65b0a1557ecdaba8829c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 10:17:40 +0100 Subject: [PATCH 55/63] emulator config changes test --- .detoxrc.js | 5 ++++- .github/workflows/run-e2e-workflow.yml | 1 - android/app/build.gradle | 4 +--- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.detoxrc.js b/.detoxrc.js index ed6ab7e05e2..0cdf6bf15f3 100644 --- a/.detoxrc.js +++ b/.detoxrc.js @@ -78,7 +78,10 @@ module.exports = { type: 'android.emulator', device: { avdName: 'emulator', - } + }, + // optimized for Bitrise CI runners + bootArgs: '-verbose -show-kernel -no-audio -netdelay none -no-snapshot -wipe-data -gpu auto -no-window -no-boot-anim -read-only', + forceAdbInstall: true, }, 'android.github_ci.emulator': { type: 'android.emulator', diff --git a/.github/workflows/run-e2e-workflow.yml b/.github/workflows/run-e2e-workflow.yml index ed7563a4249..09f6949f2bc 100644 --- a/.github/workflows/run-e2e-workflow.yml +++ b/.github/workflows/run-e2e-workflow.yml @@ -62,7 +62,6 @@ jobs: platform: ${{ inputs.platform }} setup-simulator: ${{ inputs.platform == 'ios' }} android-avd-name: emulator - android-abi: x86_64 configure-keystores: false - name: Build Detox framework cache (iOS) diff --git a/android/app/build.gradle b/android/app/build.gradle index aae71e21840..2ea8aeec71b 100644 --- a/android/app/build.gradle +++ b/android/app/build.gradle @@ -319,9 +319,7 @@ android { def env = System.getenv("METAMASK_ENVIRONMENT") def isE2E = System.getenv("E2E") - if (isE2E) { - signingConfig signingConfigs.qaProd - } else if (env == 'exp') { + if (env == 'exp') { signingConfig signingConfigs.mainExp } else if (env == 'test') { signingConfig signingConfigs.mainTest From af8127e771bcd7bbb89b966204c12c103f37e53f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:35:43 +0100 Subject: [PATCH 56/63] actionlint --- .github/workflows/actionlint.yaml | 5 +++++ .github/workflows/ci.yml | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) create mode 100644 .github/workflows/actionlint.yaml diff --git a/.github/workflows/actionlint.yaml b/.github/workflows/actionlint.yaml new file mode 100644 index 00000000000..90c21bab699 --- /dev/null +++ b/.github/workflows/actionlint.yaml @@ -0,0 +1,5 @@ +self-hosted-runner: + labels: + - "gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl" + - "gha-mmsdk-scale-set-ubuntu-22.04-amd64-large" + - "gha-mm-scale-set-ubuntu-22.04-amd64-large" diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 29d5dbbf8cf..0b075fb047b 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -306,7 +306,7 @@ jobs: run: bash <(curl https://raw.githubusercontent.com/rhysd/actionlint/62dc61a45fc95efe8c800af7a557ab0b9165d63b/scripts/download-actionlint.bash) 1.7.1 shell: bash - name: Check workflow files - run: ${{ steps.download-actionlint.outputs.executable }} -color + run: ${{ steps.download-actionlint.outputs.executable }} -color -config-file actionlint.yaml shell: bash all-jobs-pass: name: All jobs pass From e350bc3cc5a9ab668e67d162d04366f7c076abc9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:37:09 +0100 Subject: [PATCH 57/63] actionlint --- .github/{workflows => }/actionlint.yaml | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename .github/{workflows => }/actionlint.yaml (100%) diff --git a/.github/workflows/actionlint.yaml b/.github/actionlint.yaml similarity index 100% rename from .github/workflows/actionlint.yaml rename to .github/actionlint.yaml From 8a198b8e20bb2d32828481437fab7e94926203f8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:41:09 +0100 Subject: [PATCH 58/63] paths --- .github/actionlint.yaml | 19 ++++++++++++++++++- .github/workflows/ci.yml | 2 +- 2 files changed, 19 insertions(+), 2 deletions(-) diff --git a/.github/actionlint.yaml b/.github/actionlint.yaml index 90c21bab699..19f30ffc403 100644 --- a/.github/actionlint.yaml +++ b/.github/actionlint.yaml @@ -1,5 +1,22 @@ self-hosted-runner: - labels: + # Labels of self-hosted runner in array of strings. + labels: - "gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl" - "gha-mmsdk-scale-set-ubuntu-22.04-amd64-large" - "gha-mm-scale-set-ubuntu-22.04-amd64-large" + +# Configuration variables in array of strings defined in your repository or +# organization. `null` means disabling configuration variables check. +# Empty array means no configuration variable is allowed. +config-variables: null + +# Configuration for file paths. The keys are glob patterns to match to file +# paths relative to the repository root. The values are the configurations for +# the file paths. Note that the path separator is always '/'. +# The following configurations are available. +# +# "ignore" is an array of regular expression patterns. Matched error messages +# are ignored. This is similar to the "-ignore" command line option. +paths: +# .github/workflows/**/*.yml: +# ignore: [] diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 0b075fb047b..cd714dc822b 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -306,7 +306,7 @@ jobs: run: bash <(curl https://raw.githubusercontent.com/rhysd/actionlint/62dc61a45fc95efe8c800af7a557ab0b9165d63b/scripts/download-actionlint.bash) 1.7.1 shell: bash - name: Check workflow files - run: ${{ steps.download-actionlint.outputs.executable }} -color -config-file actionlint.yaml + run: ${{ steps.download-actionlint.outputs.executable }} -color -config-file .github/actionlint.yaml shell: bash all-jobs-pass: name: All jobs pass From b85588ccb79529f50360f3910d6082b589822652 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:42:45 +0100 Subject: [PATCH 59/63] ignore --- .github/actionlint.yaml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/.github/actionlint.yaml b/.github/actionlint.yaml index 19f30ffc403..67b8d6b6d47 100644 --- a/.github/actionlint.yaml +++ b/.github/actionlint.yaml @@ -18,5 +18,6 @@ config-variables: null # "ignore" is an array of regular expression patterns. Matched error messages # are ignored. This is similar to the "-ignore" command line option. paths: -# .github/workflows/**/*.yml: -# ignore: [] + .github/workflows/test-ios-build-app.yml: + ignore: + - "workflow is empty" From 1b498faa733355d752ea958c533053d3990798e4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:43:55 +0100 Subject: [PATCH 60/63] ignore --- .github/actionlint.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/actionlint.yaml b/.github/actionlint.yaml index 67b8d6b6d47..254f8507058 100644 --- a/.github/actionlint.yaml +++ b/.github/actionlint.yaml @@ -20,4 +20,4 @@ config-variables: null paths: .github/workflows/test-ios-build-app.yml: ignore: - - "workflow is empty" + - ".*" From 5a031dd3674c9ea5bb43eaa4536d5204f7398805 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:46:47 +0100 Subject: [PATCH 61/63] test --- .github/actionlint.yaml | 3 - .github/workflows/test-ios-build-app.yml | 339 +++++++++++------------ 2 files changed, 169 insertions(+), 173 deletions(-) diff --git a/.github/actionlint.yaml b/.github/actionlint.yaml index 254f8507058..b40d1528f04 100644 --- a/.github/actionlint.yaml +++ b/.github/actionlint.yaml @@ -18,6 +18,3 @@ config-variables: null # "ignore" is an array of regular expression patterns. Matched error messages # are ignored. This is similar to the "-ignore" command line option. paths: - .github/workflows/test-ios-build-app.yml: - ignore: - - ".*" diff --git a/.github/workflows/test-ios-build-app.yml b/.github/workflows/test-ios-build-app.yml index 9472b8c3a08..e770691f594 100644 --- a/.github/workflows/test-ios-build-app.yml +++ b/.github/workflows/test-ios-build-app.yml @@ -1,170 +1,169 @@ -# name: Test iOS Build QA App - -# on: -# # push: -# workflow_dispatch: -# inputs: -# retention_days: -# description: 'Number of days to retain the uploaded artifacts' -# required: false -# default: '7' -# type: string - -# permissions: -# contents: write -# id-token: write - -# jobs: -# ios-build: -# name: Test iOS QA Build App -# runs-on: macos-15 -# outputs: -# artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} -# app-uploaded: ${{ steps.upload-app.outcome == 'success' }} -# ipa-uploaded: ${{ steps.upload-ipa.outcome == 'success' }} -# archive-uploaded: ${{ steps.upload-archive.outcome == 'success' }} -# sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} -# env: -# GITHUB_CI: "true" # โœ… This ensures it's available during pod install -# steps: -# # Get the source code from the repository -# - name: Checkout repo -# uses: actions/checkout@v4 - -# # Display system information for debugging purposes -# - name: Detect CPU architecture -# run: | -# echo "Arch: $(uname -m)" -# if [[ "$(uname -m)" == "x86_64" ]]; then -# echo "Detected Intel runner" -# else -# echo "Detected Apple Silicon runner" -# fi - -# - name: Print system resources -# run: | -# echo "๐Ÿง  Memory info:" -# vm_stat -# echo "" -# echo "๐Ÿ’ป CPU info:" -# sysctl -n hw.ncpu -# sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' -# shell: bash - -# # Install Node.js, Xcode tools, and other iOS development dependencies -# - name: Installing iOS Environment Setup -# uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions -# with: -# platform: ios -# setup-simulator: false - -# - name: Print iOS tool versions -# run: | -# echo "๐Ÿ”ง Node.js Version:" -# node -v || echo "Node not found" -# echo "๐Ÿงถ Yarn Version:" -# yarn -v || echo "Yarn not found" -# echo "๐Ÿ“ฆ CocoaPods Version:" -# pod --version || echo "CocoaPods not found" -# echo "๐Ÿ› ๏ธ Xcode Path:" -# xcode-select -p || echo "Xcode not found" -# echo "๐Ÿ“ฑ Booted iOS Simulators:" -# xcrun simctl list | grep Booted || echo "No booted simulators found" -# shell: bash - -# # Run project setup and build the iOS QA app for simulator -# - name: Setup iOS Environment -# run: | -# echo "๐Ÿš€ Finishing iOS Setup..." -# yarn setup:github-ci --build-ios --no-build-android -# echo "๐Ÿ— Building iOS APP..." -# yarn build:ios:qa -# shell: bash -# env: -# PLATFORM: ios -# METAMASK_ENVIRONMENT: qa -# METAMASK_BUILD_TYPE: main -# IS_TEST: true -# IGNORE_BOXLOGS_DEVELOPMENT: true -# GITHUB_CI: "true" -# CI: "true" - -# NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners - -# SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} -# SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} -# SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} -# SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} - -# MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} -# MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} - -# MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} -# MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} -# MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} -# MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} -# MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} -# GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} -# GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} - -# # Upload the iOS .app file that works in simulators (no certificates needed) -# - name: Upload iOS APP Artifact (Simulator) -# id: upload-app -# uses: actions/upload-artifact@v4 -# with: -# name: MetaMask-QA.app -# path: ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app -# retention-days: ${{ inputs.retention_days }} -# if-no-files-found: error -# continue-on-error: true - -# # Upload iOS .ipa file for device installation (requires certificates - may not exist) -# - name: Upload iOS IPA Artifact (Device) -# id: upload-ipa -# uses: actions/upload-artifact@v4 -# with: -# name: MetaMask-QA.ipa -# path: ios/build/output/MetaMask-QA.ipa -# retention-days: ${{ inputs.retention_days }} -# if-no-files-found: error -# continue-on-error: true - -# # Upload iOS .xcarchive file for debugging and re-signing (requires certificates - may not exist) -# - name: Upload iOS Archive Artifact -# id: upload-archive -# uses: actions/upload-artifact@v4 -# with: -# name: MetaMask-QA.xcarchive -# path: ios/build/MetaMask-QA.xcarchive -# retention-days: ${{ inputs.retention_days }} -# if-no-files-found: error -# continue-on-error: true - -# # Upload source map file for crash debugging and error tracking if exists -# - name: Upload iOS Source Map -# id: upload-sourcemap -# uses: actions/upload-artifact@v4 -# with: -# name: index.js.map -# path: sourcemaps/ios/index.js.map -# retention-days: ${{ inputs.retention_days }} -# if-no-files-found: error -# continue-on-error: true - -# # Generate artifact download URL and display upload status summary -# - name: Set Artifacts URL and Status -# id: set-artifacts-url -# run: | -# ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" -# echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" -# echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" -# echo "" -# echo "Upload Status Summary:" -# echo "- APP (Simulator): ${{ steps.upload-app.outcome }}" -# echo "- IPA (Device): ${{ steps.upload-ipa.outcome }}" -# echo "- Archive: ${{ steps.upload-archive.outcome }}" -# echo "- Source Map: ${{ steps.upload-sourcemap.outcome }}" - -# env: -# GITHUB_REPOSITORY: "${{ github.repository }}" -# GITHUB_RUN_ID: "${{ github.run_id }}" +name: Test iOS Build QA App + +on: + workflow_dispatch: + inputs: + retention_days: + description: 'Number of days to retain the uploaded artifacts' + required: false + default: '7' + type: string + +permissions: + contents: write + id-token: write + +jobs: + ios-build: + name: Test iOS QA Build App + runs-on: macos-15 + outputs: + artifacts-url: ${{ steps.set-artifacts-url.outputs.artifacts-url }} + app-uploaded: ${{ steps.upload-app.outcome == 'success' }} + ipa-uploaded: ${{ steps.upload-ipa.outcome == 'success' }} + archive-uploaded: ${{ steps.upload-archive.outcome == 'success' }} + sourcemap-uploaded: ${{ steps.upload-sourcemap.outcome == 'success' }} + env: + GITHUB_CI: "true" # โœ… This ensures it's available during pod install + steps: + # Get the source code from the repository + - name: Checkout repo + uses: actions/checkout@v4 + + # Display system information for debugging purposes + - name: Detect CPU architecture + run: | + echo "Arch: $(uname -m)" + if [[ "$(uname -m)" == "x86_64" ]]; then + echo "Detected Intel runner" + else + echo "Detected Apple Silicon runner" + fi + + - name: Print system resources + run: | + echo "๐Ÿง  Memory info:" + vm_stat + echo "" + echo "๐Ÿ’ป CPU info:" + sysctl -n hw.ncpu + sysctl -n hw.memsize | awk '{ byte =$1 /1024/1024/1024; print byte " GB" }' + shell: bash + + # Install Node.js, Xcode tools, and other iOS development dependencies + - name: Installing iOS Environment Setup + uses: MetaMask/github-tools/.github/actions/setup-e2e-env@e2e-env-actions + with: + platform: ios + setup-simulator: false + + - name: Print iOS tool versions + run: | + echo "๐Ÿ”ง Node.js Version:" + node -v || echo "Node not found" + echo "๐Ÿงถ Yarn Version:" + yarn -v || echo "Yarn not found" + echo "๐Ÿ“ฆ CocoaPods Version:" + pod --version || echo "CocoaPods not found" + echo "๐Ÿ› ๏ธ Xcode Path:" + xcode-select -p || echo "Xcode not found" + echo "๐Ÿ“ฑ Booted iOS Simulators:" + xcrun simctl list | grep Booted || echo "No booted simulators found" + shell: bash + + # Run project setup and build the iOS QA app for simulator + - name: Setup iOS Environment + run: | + echo "๐Ÿš€ Finishing iOS Setup..." + yarn setup:github-ci --build-ios --no-build-android + echo "๐Ÿ— Building iOS APP..." + yarn build:ios:qa + shell: bash + env: + PLATFORM: ios + METAMASK_ENVIRONMENT: qa + METAMASK_BUILD_TYPE: main + IS_TEST: true + IGNORE_BOXLOGS_DEVELOPMENT: true + GITHUB_CI: "true" + CI: "true" + + NODE_OPTIONS: "--max_old_space_size=4096" # Increase memory limit for build, specially on GH Runners + + SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} + SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} + SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} + SEGMENT_REGULATIONS_ENDPOINT_QA: ${{ secrets.SEGMENT_REGULATIONS_ENDPOINT_QA }} + + MM_SENTRY_DSN_TEST: ${{ secrets.MM_SENTRY_DSN_TEST }} + MM_SENTRY_AUTH_TOKEN: ${{ secrets.MM_SENTRY_AUTH_TOKEN }} + + MAIN_IOS_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_IOS_GOOGLE_CLIENT_ID_UAT }} + MAIN_IOS_GOOGLE_REDIRECT_URI_UAT: ${{ secrets.MAIN_IOS_GOOGLE_REDIRECT_URI_UAT }} + MAIN_ANDROID_APPLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_APPLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_CLIENT_ID_UAT }} + MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} + GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} + GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + + # Upload the iOS .app file that works in simulators (no certificates needed) + - name: Upload iOS APP Artifact (Simulator) + id: upload-app + uses: actions/upload-artifact@v4 + with: + name: MetaMask-QA.app + path: ios/build/Build/Products/Release-iphonesimulator/MetaMask-QA.app + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error + continue-on-error: true + + # Upload iOS .ipa file for device installation (requires certificates - may not exist) + - name: Upload iOS IPA Artifact (Device) + id: upload-ipa + uses: actions/upload-artifact@v4 + with: + name: MetaMask-QA.ipa + path: ios/build/output/MetaMask-QA.ipa + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error + continue-on-error: true + + # Upload iOS .xcarchive file for debugging and re-signing (requires certificates - may not exist) + - name: Upload iOS Archive Artifact + id: upload-archive + uses: actions/upload-artifact@v4 + with: + name: MetaMask-QA.xcarchive + path: ios/build/MetaMask-QA.xcarchive + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error + continue-on-error: true + + # Upload source map file for crash debugging and error tracking if exists + - name: Upload iOS Source Map + id: upload-sourcemap + uses: actions/upload-artifact@v4 + with: + name: index.js.map + path: sourcemaps/ios/index.js.map + retention-days: ${{ inputs.retention_days }} + if-no-files-found: error + continue-on-error: true + + # Generate artifact download URL and display upload status summary + - name: Set Artifacts URL and Status + id: set-artifacts-url + run: | + ARTIFACTS_URL="https://github.com/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" + echo "artifacts-url=${ARTIFACTS_URL}" >> "$GITHUB_OUTPUT" + echo "๐Ÿ“ฆ Artifacts available at: ${ARTIFACTS_URL}" + echo "" + echo "Upload Status Summary:" + echo "- APP (Simulator): ${{ steps.upload-app.outcome }}" + echo "- IPA (Device): ${{ steps.upload-ipa.outcome }}" + echo "- Archive: ${{ steps.upload-archive.outcome }}" + echo "- Source Map: ${{ steps.upload-sourcemap.outcome }}" + + env: + GITHUB_REPOSITORY: "${{ github.repository }}" + GITHUB_RUN_ID: "${{ github.run_id }}" From e9ce79a1e3b5ccc280b625bd2d65e89f054fbe4f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:47:27 +0100 Subject: [PATCH 62/63] actionlint --- .github/actionlint.yaml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/actionlint.yaml b/.github/actionlint.yaml index b40d1528f04..c851a1c3fff 100644 --- a/.github/actionlint.yaml +++ b/.github/actionlint.yaml @@ -4,6 +4,7 @@ self-hosted-runner: - "gha-mmsdk-scale-set-ubuntu-22.04-amd64-xl" - "gha-mmsdk-scale-set-ubuntu-22.04-amd64-large" - "gha-mm-scale-set-ubuntu-22.04-amd64-large" + - "macos-15" # Configuration variables in array of strings defined in your repository or # organization. `null` means disabling configuration variables check. From f749d93630f9cb10fdb371c08eb44643229dc88a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o?= Date: Thu, 7 Aug 2025 13:54:56 +0100 Subject: [PATCH 63/63] add new vars for e2e --- .github/workflows/build-android-e2e.yml | 5 +++++ .github/workflows/run-e2e-workflow.yml | 5 +++++ 2 files changed, 10 insertions(+) diff --git a/.github/workflows/build-android-e2e.yml b/.github/workflows/build-android-e2e.yml index 8814466199e..690234a2d02 100644 --- a/.github/workflows/build-android-e2e.yml +++ b/.github/workflows/build-android-e2e.yml @@ -68,6 +68,10 @@ jobs: GITHUB_CI: "true" CI: "true" NODE_OPTIONS: "--max-old-space-size=8192" + MM_UNIFIED_SWAPS_ENABLED: "true" + MM_BRIDGE_ENABLED: "true" + BRIDGE_USE_DEV_APIS: "true" + RAMP_INTERNAL_BUILD: "true" SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} SEGMENT_DELETE_API_SOURCE_ID_QA: ${{ secrets.SEGMENT_DELETE_API_SOURCE_ID_QA }} @@ -81,6 +85,7 @@ jobs: MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT: ${{ secrets.MAIN_ANDROID_GOOGLE_SERVER_CLIENT_ID_UAT }} GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} + MM_INFURA_PROJECT_ID: ${{ secrets.MM_INFURA_PROJECT_ID }} - name: Upload Android APK id: upload-apk diff --git a/.github/workflows/run-e2e-workflow.yml b/.github/workflows/run-e2e-workflow.yml index 09f6949f2bc..d964ac1dd50 100644 --- a/.github/workflows/run-e2e-workflow.yml +++ b/.github/workflows/run-e2e-workflow.yml @@ -32,6 +32,10 @@ jobs: METAMASK_BUILD_TYPE: 'main' TEST_SUITE_TAG: ${{ inputs.test_suite_tag }} GITHUB_CI: 'true' + MM_UNIFIED_SWAPS_ENABLED: 'true' + RAMP_INTERNAL_BUILD: 'true' + MM_BRIDGE_ENABLED: 'true' + BRIDGE_USE_DEV_APIS: 'true' MM_TEST_WALLET_SRP: ${{ secrets.MM_TEST_WALLET_SRP }} SEGMENT_WRITE_KEY_QA: ${{ secrets.SEGMENT_WRITE_KEY_QA }} SEGMENT_PROXY_URL_QA: ${{ secrets.SEGMENT_PROXY_URL_QA }} @@ -47,6 +51,7 @@ jobs: GOOGLE_SERVICES_B64_IOS: ${{ secrets.GOOGLE_SERVICES_B64_IOS }} GOOGLE_SERVICES_B64_ANDROID: ${{ secrets.GOOGLE_SERVICES_B64_ANDROID }} MM_SOLANA_E2E_TEST_SRP: ${{ secrets.MM_SOLANA_E2E_TEST_SRP }} + MM_INFURA_PROJECT_ID: ${{ secrets.MM_INFURA_PROJECT_ID }} steps: - name: Checkout