Skip to content

fix: workaround expo-modules-core swift 6 compiler crash on iOS builds #1487

fix: workaround expo-modules-core swift 6 compiler crash on iOS builds

fix: workaround expo-modules-core swift 6 compiler crash on iOS builds #1487

name: iOS Native Tests
env:
# Specify an iOS version to test on.
simulator_ios_version: 17
# Name of the simulator device to use.
simulator_device_name: iPhone 15 Pro
on:
push:
branches:
- main
- ci/native-tests-free-runners
- react-native-82
paths:
- '.github/actions/install/**'
- '.github/workflows/build-ios-test-container-app.yml'
- '.github/workflows/test-native-ios.yml'
- 'bun.lock'
- 'package.json'
- 'packages/one/metro-entry.js'
- 'packages/one/metro-entry-ctx.js'
- 'packages/one/src/**/*.native.*'
- 'packages/one/src/**/*.ios.*'
- 'packages/one/src/**/*.android.*'
- 'packages/one/src/cli/prebuild.ts'
- 'packages/one/src/cli/runAndroid.ts'
- 'packages/one/src/cli/runIos.ts'
- 'packages/one/src/metro-config/**'
- 'packages/vite-plugin-metro/**'
- 'packages/vxrn/**'
- 'tests/rn-test-container/app.json'
- 'tests/rn-test-container/e2e/**'
- 'tests/rn-test-container/ios/**'
- 'tests/rn-test-container/package.json'
- 'tests/rn-test-container/react-native.config.cjs'
- 'tests/rn-test-container/scripts/**'
workflow_dispatch:
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: ${{ github.ref != 'refs/heads/main' }}
jobs:
build-ios-test-container-dev:
name: Build iOS RN Test App (Dev)
uses: ./.github/workflows/build-ios-test-container-app.yml
secrets: inherit
permissions:
contents: read
pull-requests: read
with:
configuration: Debug
build-ios-test-container-prod:
name: Build iOS RN Test App (Prod)
uses: ./.github/workflows/build-ios-test-container-app.yml
secrets: inherit
permissions:
contents: read
pull-requests: read
with:
configuration: Release
test-ios-native:
name: Native iOS Tests
needs:
- build-ios-test-container-dev
- build-ios-test-container-prod
runs-on: macos-14
timeout-minutes: 60
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Install
uses: ./.github/actions/install
with:
install-playwright: 'false'
- name: Download Built Test Container App (Dev)
uses: actions/cache/restore@v4
with:
fail-on-cache-miss: true
key: ${{ needs.build-ios-test-container-dev.outputs.built-app-cache-key }}
path: ${{ needs.build-ios-test-container-dev.outputs.built-app-path }}
- name: Download Built Test Container App (Prod)
uses: actions/cache/restore@v4
with:
fail-on-cache-miss: true
key: ${{ needs.build-ios-test-container-prod.outputs.built-app-cache-key }}
path: ${{ needs.build-ios-test-container-prod.outputs.built-app-path }}
- name: Get Simulator UDID
id: get-simulator-udid
env:
SIMULATOR_IOS_VERSION: ${{ env.simulator_ios_version }}
SIMULATOR_DEVICE_NAME: ${{ env.simulator_device_name }}
run: |
AVAILABLE_SIMULATORS=$(xcrun simctl list devices available --json | jq -r '[.devices | to_entries[] | select(.key | contains("SimRuntime.iOS")) | .key as $runtime | .value[] | { runtime: $runtime, name: .name, udid: .udid }]')
echo "Available simulators: $AVAILABLE_SIMULATORS"
SELECTED_SIMULATOR=$(echo $AVAILABLE_SIMULATORS | jq -r "[.[] | select(.runtime | contains(\"$SIMULATOR_IOS_VERSION\")) | select(.name == \"$SIMULATOR_DEVICE_NAME\")] | first")
if [ -z "$SELECTED_SIMULATOR" ] || [ "$SELECTED_SIMULATOR" = "null" ]; then
echo "Error: No simulator found for iOS version $SIMULATOR_IOS_VERSION and device name $SIMULATOR_DEVICE_NAME"
echo "Available devices:"
echo "$AVAILABLE_SIMULATORS" | jq -r '.[] | "\(.name) (\(.runtime))"'
exit 1
fi
echo "Selected simulator: $SELECTED_SIMULATOR"
SIMULATOR_UDID=$(echo $SELECTED_SIMULATOR | jq -r .udid)
if [ -z "$SIMULATOR_UDID" ] || [ "$SIMULATOR_UDID" = "null" ]; then
echo "Error: Could not get simulator UDID"
exit 1
fi
echo "Simulator UDID: $SIMULATOR_UDID"
echo "simulator_udid=$SIMULATOR_UDID" >> $GITHUB_OUTPUT
- name: Boot Simulator
env:
SIMULATOR_UDID: ${{ steps.get-simulator-udid.outputs.simulator_udid }}
run: xcrun simctl boot $SIMULATOR_UDID
- name: Cache Appium
id: appium-cache
uses: actions/cache@v4
with:
path: |
~/.appium
/usr/local/lib/node_modules/appium
/usr/local/bin/appium
key: appium-xcuitest-${{ runner.os }}-v1
- name: Install Appium
if: steps.appium-cache.outputs.cache-hit != 'true'
run: |
npm install -g appium
appium driver install xcuitest
- name: Verify Appium
run: |
# ensure cached appium is functional (symlink can break)
if ! appium --version 2>/dev/null; then
echo "appium not functional, reinstalling..."
npm install -g appium
fi
appium --version
- name: Start Appium Server
run: |
appium > /tmp/appium.log 2>&1 &
# wait for appium to be ready
for i in {1..30}; do
if curl -s http://localhost:4723/status | grep -q '"ready":true'; then
echo "Appium ready after $i seconds"
break
fi
if [ $i -eq 30 ]; then
echo "Appium failed to start"
cat /tmp/appium.log
exit 1
fi
sleep 1
done
- name: Test Dev
env:
SIMULATOR_UDID: ${{ steps.get-simulator-udid.outputs.simulator_udid }}
IOS_TEST_CONTAINER_PATH_DEV: ${{ github.workspace }}/${{ needs.build-ios-test-container-dev.outputs.built-app-path }}
run: |
bun run --filter test-test test-ios:dev
- name: Test Prod
env:
SIMULATOR_UDID: ${{ steps.get-simulator-udid.outputs.simulator_udid }}
IOS_TEST_CONTAINER_PATH_PROD: ${{ github.workspace }}/${{ needs.build-ios-test-container-prod.outputs.built-app-path }}
run: |
bun run --filter test-test test-ios:prod
- name: Upload Appium Logs
uses: actions/upload-artifact@v4.3.1
if: ${{ always() }}
continue-on-error: true
with:
name: appium-tests.log
path: /tmp/appium.log
- name: Upload Appium Screenshots
uses: actions/upload-artifact@v4.3.1
if: ${{ always() }}
continue-on-error: true
with:
name: appium-screenshots
path: /tmp/appium-screenshots