From 98de98eda815cde1fa0ecd4bbbe53d65065d8f93 Mon Sep 17 00:00:00 2001 From: Chris Conlon Date: Tue, 30 Dec 2025 13:10:19 -0700 Subject: [PATCH] Testing: update Android GitHub workflow to run tests on emulator --- .github/workflows/android_gradle.yml | 107 ++++++++++++++++++++------- .github/workflows/main.yml | 15 ---- 2 files changed, 81 insertions(+), 41 deletions(-) diff --git a/.github/workflows/android_gradle.yml b/.github/workflows/android_gradle.yml index 031961b4..d5c5180a 100644 --- a/.github/workflows/android_gradle.yml +++ b/.github/workflows/android_gradle.yml @@ -1,21 +1,18 @@ -name: Android Gradle Build test logic +name: Android Gradle Build and Test on: - workflow_call: - inputs: - os: - required: true - type: string - jdk_distro: - required: true - type: string - jdk_version: - required: true - type: string + push: + branches: [ 'master', 'main', 'release/**' ] + pull_request: + branches: [ 'master' ] + +concurrency: + group: android-${{ github.head_ref || github.ref }} + cancel-in-progress: true jobs: - build_wolfssljni: - runs-on: ${{ inputs.os }} + build_wolfcryptjni: + runs-on: ubuntu-latest steps: - name: Clone wolfcrypt-jni uses: actions/checkout@v4 @@ -31,22 +28,80 @@ jobs: - name: Create blank options.h run: cp IDE/Android/app/src/main/cpp/wolfssl/wolfssl/options.h.in IDE/Android/app/src/main/cpp/wolfssl/wolfssl/options.h - # Setup Java + # Setup Java with Gradle caching - name: Setup java uses: actions/setup-java@v4 with: - distribution: ${{ inputs.jdk_distro }} - java-version: ${{ inputs.jdk_version }} + distribution: 'zulu' + java-version: '21' + cache: 'gradle' - # Gradle assembleDebug - - name: Gradle assembleDebug - run: cd IDE/Android && ls && ./gradlew assembleDebug + # Build all targets in single Gradle invocation + - name: Gradle Build + run: cd IDE/Android && ./gradlew --build-cache assembleDebug assembleDebugUnitTest assembleDebugAndroidTest - # Gradle assembleDebugUnitTest - - name: Gradle assembleDebugUnitTest - run: cd IDE/Android && ls && ./gradlew assembleDebugUnitTest + # Enable KVM for hardware acceleration (required for emulator) + - name: Enable KVM + run: | + echo 'KERNEL=="kvm", GROUP="kvm", MODE="0666", OPTIONS+="static_node=kvm"' | sudo tee /etc/udev/rules.d/99-kvm4all.rules + sudo udevadm control --reload-rules + sudo udevadm trigger --name-match=kvm - # Gradle assembleDebugAndroidTest - - name: Gradle assembleDebugAndroidTest - run: cd IDE/Android && ls && ./gradlew assembleDebugAndroidTest + # Cache AVD snapshot for faster emulator boot + - name: AVD cache + uses: actions/cache@v4 + id: avd-cache + with: + path: | + ~/.android/avd/* + ~/.android/adb* + key: avd-wolfcryptjni-30-x86_64-atd-v1 + # Create AVD and generate snapshot for caching + - name: Create AVD and generate snapshot + if: steps.avd-cache.outputs.cache-hit != 'true' + uses: reactivecircus/android-emulator-runner@v2 + with: + api-level: 30 + arch: x86_64 + target: aosp_atd + force-avd-creation: false + emulator-options: -no-window -gpu swiftshader_indirect -noaudio -no-boot-anim -camera-back none + disable-animations: true + script: echo "Generated AVD snapshot for caching" + + # Run instrumented tests on Android emulator + - name: Run Android Instrumented Tests + uses: reactivecircus/android-emulator-runner@v2 + timeout-minutes: 15 + with: + api-level: 30 + arch: x86_64 + target: aosp_atd + force-avd-creation: false + emulator-options: -no-snapshot-save -no-window -gpu swiftshader_indirect -noaudio -no-boot-anim -camera-back none + disable-animations: true + script: | + adb wait-for-device + adb shell mkdir -p /data/local/tmp/examples/certs/intermediate + adb shell mkdir -p /data/local/tmp/examples/certs/rsapss + adb shell mkdir -p /data/local/tmp/examples/certs/crl + adb push ./examples/certs/ /data/local/tmp/examples/ + adb logcat -c + cd IDE/Android && ./gradlew connectedDebugAndroidTest --no-daemon --no-watch-fs || { adb logcat -d > /tmp/logcat.txt 2>&1; echo "=== LOGCAT (errors) ==="; grep -i "exception\|error\|fatal" /tmp/logcat.txt || true; exit 1; } + adb logcat -d > /tmp/logcat.txt 2>&1 || true + pgrep -f '[q]emu-system' | xargs -r kill -9 2>/dev/null || true + pgrep -f '[c]rashpad' | xargs -r kill -9 2>/dev/null || true + sleep 2 + + # Upload test reports even on failure + - name: Upload Test Reports + uses: actions/upload-artifact@v4 + if: always() + timeout-minutes: 5 + with: + name: android-test-reports + path: | + IDE/Android/app/build/reports/androidTests/ + /tmp/logcat.txt + retention-days: 14 diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 7925c24a..047398b3 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -139,21 +139,6 @@ jobs: jdk_version: ${{ matrix.jdk_version }} wolfssl_configure: ${{ matrix.wolfssl_configure }} - # ----------------------- Android Gradle build ------------------------ - # Run Android gradle build over PR code, only running on Linux with one - # JDK/version for now. - android-gradle: - strategy: - matrix: - os: [ 'ubuntu-latest' ] - jdk_version: [ '21' ] - name: Android Gradle (${{ matrix.os }} Zulu JDK ${{ matrix.jdk_version }}) - uses: ./.github/workflows/android_gradle.yml - with: - os: ${{ matrix.os }} - jdk_distro: "zulu" - jdk_version: ${{ matrix.jdk_version }} - # --------------------- Maven build - test pom.xml -------------------- # Run Maven build over PR code, running on Linux and Mac with only one # JDK/version for now.