From 41950ae33e8bf1e0c47c0d6168b7ec04bbad4c42 Mon Sep 17 00:00:00 2001 From: Nicoole Date: Mon, 24 Aug 2026 17:37:07 -0400 Subject: [PATCH 1/4] Added android matrix RN compatbility --- .github/workflows/android.yml | 68 ++++++++++++++++++++++++++--------- 1 file changed, 52 insertions(+), 16 deletions(-) diff --git a/.github/workflows/android.yml b/.github/workflows/android.yml index 1332d0b6..88126c29 100644 --- a/.github/workflows/android.yml +++ b/.github/workflows/android.yml @@ -39,12 +39,6 @@ jobs: fail-fast: false matrix: os: [ubuntu-latest, windows-latest] - react-native: [0.87.0] - react: [19.2.8] - include: - - os: ubuntu-latest - react-native: 0.82.0 - react: 19.1.1 defaults: run: shell: bash @@ -65,19 +59,61 @@ jobs: path: | node_modules */*/node_modules - key: ${{ runner.os }}-rn-${{ matrix.react-native }}-${{ hashFiles('**/yarn.lock') }} + key: ${{ runner.os }}-${{ hashFiles('**/yarn.lock') }} - name: Install dependencies run: yarn install - - name: Install React Native ${{ matrix.react-native }} example dependencies - run: yarn add --exact "react@${{ matrix.react }}" "react-native@${{ matrix.react-native }}" + - name: Install example app dependencies + run: yarn install working-directory: example - - name: Use RN 0.82-compatible Gradle - if: matrix.react-native == '0.82.0' - run: sed -i 's/gradle-9.4.1-bin.zip/gradle-9.0.0-bin.zip/' example/android/gradle/wrapper/gradle-wrapper.properties - name: Build Android example app - if: matrix.react-native != '0.82.0' run: ./.github/scripts/build-android.sh - - name: Compile library against the RN floor - if: matrix.react-native == '0.82.0' - run: ./gradlew :react-native-safe-area-context:compileDebugKotlin + + android-compatibility: + name: Android compatibility (RN ${{ matrix.react-native }}) + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + include: + - react-native: '0.82.0' + react: '19.1.1' + - react-native: '0.83.0' + react: '19.2.0' + - react-native: '0.84.0' + react: '19.2.3' + - react-native: '0.85.0' + react: '19.2.3' + - react-native: '0.86.0' + react: '19.2.3' + - react-native: '0.87.0' + react: '19.2.3' + steps: + - uses: actions/checkout@v4 + - name: Use Node.js 22.13.0 + uses: actions/setup-node@v4 + with: + node-version: 22.13.0 + - uses: actions/setup-java@v2 + with: + distribution: 'temurin' + java-version: '17' + - name: Restore dependencies + uses: actions/cache@v3 + with: + path: | + node_modules + example/node_modules + key: ${{ runner.os }}-compat-rn-${{ matrix.react-native }}-${{ hashFiles('**/yarn.lock') }} + - name: Install library dependencies + run: yarn install + - name: Prepare minimal compatibility app + working-directory: example + run: | + npm pkg delete 'dependencies.@react-native-async-storage/async-storage' + npm pkg delete 'dependencies.react-native-gesture-handler' + npm pkg delete 'dependencies.react-native-screens' + yarn add --exact "react@${{ matrix.react }}" "react-native@${{ matrix.react-native }}" + cp node_modules/@react-native/gradle-plugin/gradle/wrapper/gradle-wrapper.properties android/gradle/wrapper/gradle-wrapper.properties + - name: Build compatibility app working-directory: example/android + run: ./gradlew assembleDebug -PreactNativeArchitectures=x86_64 From 6a3e1aa2eb197a684bf09ad5f66e10552dd737f3 Mon Sep 17 00:00:00 2001 From: Nicoole Date: Mon, 24 Aug 2026 17:55:41 -0400 Subject: [PATCH 2/4] matrix ios --- .github/workflows/ios.yml | 63 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 63 insertions(+) diff --git a/.github/workflows/ios.yml b/.github/workflows/ios.yml index 35493f3f..cfbe1830 100644 --- a/.github/workflows/ios.yml +++ b/.github/workflows/ios.yml @@ -59,3 +59,66 @@ jobs: - name: Build ios example app run: xcodebuild -scheme ReactTestApp -workspace RNSACExample.xcworkspace ONLY_ACTIVE_ARCH=NO -sdk iphonesimulator -configuration Debug working-directory: example/ios + + ios-compatibility: + name: iOS compatibility (RN ${{ matrix.react-native }}) + runs-on: macos-15 + strategy: + fail-fast: false + matrix: + include: + - react-native: '0.82.0' + react: '19.1.1' + - react-native: '0.83.0' + react: '19.2.0' + - react-native: '0.84.0' + react: '19.2.3' + - react-native: '0.85.0' + react: '19.2.3' + - react-native: '0.86.0' + react: '19.2.3' + - react-native: '0.87.0' + react: '19.2.3' + steps: + - uses: actions/checkout@v4 + - name: Use Node.js 22.13.0 + uses: actions/setup-node@v4 + with: + node-version: 22.13.0 + - uses: ruby/setup-ruby@v1 + with: + ruby-version: 3.2 + working-directory: example + bundler-cache: true + - name: Cache dependencies + uses: actions/cache@v4 + with: + path: | + node_modules + example/node_modules + key: ${{ runner.os }}-ios-compat-rn-${{ matrix.react-native }}-${{ hashFiles('yarn.lock', 'example/yarn.lock') }} + - name: Install dependencies + run: yarn install + - name: Prepare minimal app for RN ${{ matrix.react-native }} + working-directory: example + run: | + npm pkg delete dependencies.@react-native-async-storage/async-storage + npm pkg delete dependencies.react-native-gesture-handler + npm pkg delete dependencies.react-native-screens + yarn add --exact react@${{ matrix.react }} react-native@${{ matrix.react-native }} + - name: Install pods + working-directory: example/ios + run: | + rm -f Podfile.lock + bundle exec pod install + - name: Build iOS example app + working-directory: example/ios + run: | + xcodebuild \ + -scheme ReactTestApp \ + -workspace RNSACExample.xcworkspace \ + -destination 'generic/platform=iOS Simulator' \ + -configuration Debug \ + CODE_SIGNING_ALLOWED=NO \ + ONLY_ACTIVE_ARCH=NO \ + build From 249625a19a07185d5676614335da555d45baa87d Mon Sep 17 00:00:00 2001 From: Nicoole Date: Tue, 25 Aug 2026 16:04:14 -0400 Subject: [PATCH 3/4] no message --- .github/workflows/android.yml | 50 ------- .github/workflows/compatibility.yml | 102 +++++++++++++ .github/workflows/ios.yml | 63 -------- compatibility.json | 5 + scripts/test-project | 220 ++++++++++++++++++++++++++++ 5 files changed, 327 insertions(+), 113 deletions(-) create mode 100644 .github/workflows/compatibility.yml create mode 100644 compatibility.json create mode 100755 scripts/test-project diff --git a/.github/workflows/android.yml b/.github/workflows/android.yml index 88126c29..801e305d 100644 --- a/.github/workflows/android.yml +++ b/.github/workflows/android.yml @@ -67,53 +67,3 @@ jobs: working-directory: example - name: Build Android example app run: ./.github/scripts/build-android.sh - - android-compatibility: - name: Android compatibility (RN ${{ matrix.react-native }}) - runs-on: ubuntu-latest - strategy: - fail-fast: false - matrix: - include: - - react-native: '0.82.0' - react: '19.1.1' - - react-native: '0.83.0' - react: '19.2.0' - - react-native: '0.84.0' - react: '19.2.3' - - react-native: '0.85.0' - react: '19.2.3' - - react-native: '0.86.0' - react: '19.2.3' - - react-native: '0.87.0' - react: '19.2.3' - steps: - - uses: actions/checkout@v4 - - name: Use Node.js 22.13.0 - uses: actions/setup-node@v4 - with: - node-version: 22.13.0 - - uses: actions/setup-java@v2 - with: - distribution: 'temurin' - java-version: '17' - - name: Restore dependencies - uses: actions/cache@v3 - with: - path: | - node_modules - example/node_modules - key: ${{ runner.os }}-compat-rn-${{ matrix.react-native }}-${{ hashFiles('**/yarn.lock') }} - - name: Install library dependencies - run: yarn install - - name: Prepare minimal compatibility app - working-directory: example - run: | - npm pkg delete 'dependencies.@react-native-async-storage/async-storage' - npm pkg delete 'dependencies.react-native-gesture-handler' - npm pkg delete 'dependencies.react-native-screens' - yarn add --exact "react@${{ matrix.react }}" "react-native@${{ matrix.react-native }}" - cp node_modules/@react-native/gradle-plugin/gradle/wrapper/gradle-wrapper.properties android/gradle/wrapper/gradle-wrapper.properties - - name: Build compatibility app - working-directory: example/android - run: ./gradlew assembleDebug -PreactNativeArchitectures=x86_64 diff --git a/.github/workflows/compatibility.yml b/.github/workflows/compatibility.yml new file mode 100644 index 00000000..2905f92d --- /dev/null +++ b/.github/workflows/compatibility.yml @@ -0,0 +1,102 @@ +name: Compatibility build + +on: + push: + branches: + - main + paths: + - '.github/workflows/compatibility.yml' + - 'android/**' + - 'babel.config.js' + - 'common/**' + - 'compatibility.json' + - 'ios/**' + - 'package.json' + - 'react-native-safe-area-context.podspec' + - 'react-native.config.js' + - 'scripts/test-project' + - 'src/**' + - 'tsconfig.json' + - 'yarn.lock' + pull_request: + paths: + - '.github/workflows/compatibility.yml' + - 'android/**' + - 'babel.config.js' + - 'common/**' + - 'compatibility.json' + - 'ios/**' + - 'package.json' + - 'react-native-safe-area-context.podspec' + - 'react-native.config.js' + - 'scripts/test-project' + - 'src/**' + - 'tsconfig.json' + - 'yarn.lock' + workflow_dispatch: + +permissions: + contents: read + +jobs: + read-compatibility: + runs-on: ubuntu-latest + outputs: + react-native-versions: ${{ steps.matrix.outputs.versions }} + steps: + - uses: actions/checkout@v4 + - name: Read supported React Native versions + id: matrix + run: | + versions=$(node -e " + const compatibility = require('./compatibility.json'); + process.stdout.write( + JSON.stringify(compatibility['6.x']['react-native']) + ); + ") + echo "versions=$versions" >> "$GITHUB_OUTPUT" + + android: + name: Android (RN ${{ matrix.react-native }}) + needs: read-compatibility + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + react-native: ${{ fromJSON(needs.read-compatibility.outputs.react-native-versions) }} + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version: 22.13.0 + - uses: actions/setup-java@v4 + with: + distribution: temurin + java-version: 17 + - run: yarn install + - name: Build fresh Android app + run: ./scripts/test-project --version ${{ matrix.react-native }} --platforms android + + ios: + name: iOS (RN ${{ matrix.react-native }}) + needs: read-compatibility + runs-on: macos-15 + strategy: + fail-fast: false + matrix: + react-native: ${{ fromJSON(needs.read-compatibility.outputs.react-native-versions) }} + steps: + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 + with: + node-version: 22.13.0 + - uses: ruby/setup-ruby@v1 + with: + ruby-version: 3.2 + - name: Select Xcode 16.4 + run: | + sudo xcode-select --switch /Applications/Xcode_16.4.app + xcodebuild -version + - run: yarn install + - name: Build fresh iOS app + run: ./scripts/test-project --version ${{ matrix.react-native }} --platforms ios diff --git a/.github/workflows/ios.yml b/.github/workflows/ios.yml index cfbe1830..35493f3f 100644 --- a/.github/workflows/ios.yml +++ b/.github/workflows/ios.yml @@ -59,66 +59,3 @@ jobs: - name: Build ios example app run: xcodebuild -scheme ReactTestApp -workspace RNSACExample.xcworkspace ONLY_ACTIVE_ARCH=NO -sdk iphonesimulator -configuration Debug working-directory: example/ios - - ios-compatibility: - name: iOS compatibility (RN ${{ matrix.react-native }}) - runs-on: macos-15 - strategy: - fail-fast: false - matrix: - include: - - react-native: '0.82.0' - react: '19.1.1' - - react-native: '0.83.0' - react: '19.2.0' - - react-native: '0.84.0' - react: '19.2.3' - - react-native: '0.85.0' - react: '19.2.3' - - react-native: '0.86.0' - react: '19.2.3' - - react-native: '0.87.0' - react: '19.2.3' - steps: - - uses: actions/checkout@v4 - - name: Use Node.js 22.13.0 - uses: actions/setup-node@v4 - with: - node-version: 22.13.0 - - uses: ruby/setup-ruby@v1 - with: - ruby-version: 3.2 - working-directory: example - bundler-cache: true - - name: Cache dependencies - uses: actions/cache@v4 - with: - path: | - node_modules - example/node_modules - key: ${{ runner.os }}-ios-compat-rn-${{ matrix.react-native }}-${{ hashFiles('yarn.lock', 'example/yarn.lock') }} - - name: Install dependencies - run: yarn install - - name: Prepare minimal app for RN ${{ matrix.react-native }} - working-directory: example - run: | - npm pkg delete dependencies.@react-native-async-storage/async-storage - npm pkg delete dependencies.react-native-gesture-handler - npm pkg delete dependencies.react-native-screens - yarn add --exact react@${{ matrix.react }} react-native@${{ matrix.react-native }} - - name: Install pods - working-directory: example/ios - run: | - rm -f Podfile.lock - bundle exec pod install - - name: Build iOS example app - working-directory: example/ios - run: | - xcodebuild \ - -scheme ReactTestApp \ - -workspace RNSACExample.xcworkspace \ - -destination 'generic/platform=iOS Simulator' \ - -configuration Debug \ - CODE_SIGNING_ALLOWED=NO \ - ONLY_ACTIVE_ARCH=NO \ - build diff --git a/compatibility.json b/compatibility.json new file mode 100644 index 00000000..2741f32f --- /dev/null +++ b/compatibility.json @@ -0,0 +1,5 @@ +{ + "6.x": { + "react-native": ["0.82.0", "0.83.0", "0.84.0", "0.85.0", "0.86.0", "0.87.0"] + } +} diff --git a/scripts/test-project b/scripts/test-project new file mode 100755 index 00000000..8eb56ccb --- /dev/null +++ b/scripts/test-project @@ -0,0 +1,220 @@ +#!/bin/bash + +set -euo pipefail +IFS=$'\n\t' + +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +REPO_ROOT="$(cd "$SCRIPT_DIR/.." && pwd)" +DEFAULT_PROJECT_NAME="SafeAreaContextTest" +DEFAULT_PLATFORMS="android" +RNC_CLI_VERSION="${RNC_CLI_VERSION:-20.2.0}" + +usage() { + cat <<'USAGE' +Create a throwaway React Native app that depends on the current +react-native-safe-area-context checkout, and build it. + +USAGE: + ./scripts/test-project --version [options] + +REQUIRED ARGUMENTS: + --version, -v React Native version to init the test app with + +OPTIONS: + --platforms Comma separated list: android, ios. Default: android + --release Build Release instead of Debug + --project-name Name of the temporary project. Default: SafeAreaContextTest + --keep-project Do not delete the temp project (for debugging failures) + -h, --help Print this message + +ENVIRONMENT: + RNC_CLI_VERSION @react-native-community/cli version used for `init`. + Default: 20.2.0. +USAGE +} + +RN_VERSION="" +PLATFORMS="$DEFAULT_PLATFORMS" +PROJECT_NAME="$DEFAULT_PROJECT_NAME" +KEEP_PROJECT=0 +BUILD_CONFIG="Debug" + +while [[ $# -gt 0 ]]; do + case "$1" in + --version|-v) + RN_VERSION=${2:-} + if [[ -z "$RN_VERSION" ]]; then + echo "Error! --version requires a value." >&2 + usage + exit 1 + fi + shift 2 + ;; + --platforms) + PLATFORMS=${2:-} + if [[ -z "$PLATFORMS" ]]; then + echo "Error! --platforms requires a value." >&2 + usage + exit 1 + fi + shift 2 + ;; + --project-name) + PROJECT_NAME=${2:-} + if [[ -z "$PROJECT_NAME" ]]; then + echo "Error! --project-name requires a value." >&2 + usage + exit 1 + fi + shift 2 + ;; + --release) + BUILD_CONFIG="Release" + shift + ;; + --keep-project) + KEEP_PROJECT=1 + shift + ;; + -h|--help) + usage + exit 0 + ;; + *) + echo "Error! Unknown argument: $1" >&2 + usage + exit 1 + ;; + esac +done + +if [[ -z "$RN_VERSION" ]]; then + echo "Error! Missing required --version argument." >&2 + usage + exit 1 +fi + +RUN_ANDROID=0 +RUN_IOS=0 +IFS=',' read -r -a PLATFORM_ARRAY <<< "$PLATFORMS" +for PLATFORM in "${PLATFORM_ARRAY[@]}"; do + case "${PLATFORM// }" in + android) RUN_ANDROID=1 ;; + ios) RUN_IOS=1 ;; + "") ;; + *) + echo "Error! Unknown platform: ${PLATFORM}" >&2 + exit 1 + ;; + esac +done +IFS=$'\n\t' + +if [[ $RUN_ANDROID -eq 0 && $RUN_IOS -eq 0 ]]; then + echo "Error! At least one platform must be selected." >&2 + exit 1 +fi + +TMP_DIR="$(mktemp -d)" +PROJECT_DIR="$TMP_DIR/$PROJECT_NAME" + +cleanup() { + if [[ $KEEP_PROJECT -eq 1 ]]; then + echo "Temporary project preserved at: $PROJECT_DIR" + return + fi + if [[ -d "$TMP_DIR" ]]; then + rm -rf "$TMP_DIR" + fi +} +trap cleanup EXIT + +cd "$REPO_ROOT" + +echo "==> Packing react-native-safe-area-context" +PACK_OUTPUT="$(npm pack --pack-destination "$TMP_DIR")" +TARBALL_FILENAME="$(echo "$PACK_OUTPUT" | tail -n 1 | tr -d '\r\n')" +TARBALL_PATH="$TMP_DIR/$TARBALL_FILENAME" + +echo "==> Creating React Native $RN_VERSION project ($PROJECT_NAME) in $TMP_DIR" +cd "$TMP_DIR" +npx "@react-native-community/cli@$RNC_CLI_VERSION" init "$PROJECT_NAME" \ + --version "$RN_VERSION" \ + --skip-git-init \ + --install-pods false + +echo "==> Installing local tarball" +cd "$PROJECT_DIR" +npm install "file:$TARBALL_PATH" + +echo "==> Writing smoke-test App.tsx" +cat > App.tsx <<'APP' +import React from 'react'; +import { Text } from 'react-native'; +import { + SafeAreaProvider, + SafeAreaView, + useSafeAreaInsets, +} from 'react-native-safe-area-context'; + +function Inner() { + const insets = useSafeAreaInsets(); + return ( + + {`top: ${insets.top}`} + + ); +} + +export default function App() { + return ( + + + + ); +} +APP + +if [[ $RUN_ANDROID -eq 1 ]]; then + echo "==> Bundling JavaScript for Android" + npx react-native bundle \ + --entry-file index.js \ + --platform android \ + --dev false \ + --bundle-output "$TMP_DIR/main.android.jsbundle" + + echo "==> Building Android ($BUILD_CONFIG)" + ( + cd android + ./gradlew "assemble$BUILD_CONFIG" --console=plain + ) +fi + +if [[ $RUN_IOS -eq 1 ]]; then + echo "==> Bundling JavaScript for iOS" + npx react-native bundle \ + --entry-file index.js \ + --platform ios \ + --dev false \ + --bundle-output "$TMP_DIR/main.ios.jsbundle" + + echo "==> Installing iOS dependencies" + bundle install + ( + cd ios + bundle exec pod install + + echo "==> Building iOS ($BUILD_CONFIG)" + xcodebuild \ + -workspace "$PROJECT_NAME.xcworkspace" \ + -configuration "$BUILD_CONFIG" \ + -scheme "$PROJECT_NAME" \ + -destination 'generic/platform=iOS Simulator' \ + -derivedDataPath "$TMP_DIR/DerivedData" \ + CODE_SIGNING_ALLOWED=NO \ + ONLY_ACTIVE_ARCH=NO \ + -quiet + ) +fi + +echo "==> All requested builds finished successfully." From 85cda5354224e339a87596278674146c64fe151a Mon Sep 17 00:00:00 2001 From: Nicoole Date: Tue, 25 Aug 2026 17:15:13 -0400 Subject: [PATCH 4/4] no message --- example/ios/Podfile.lock | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/example/ios/Podfile.lock b/example/ios/Podfile.lock index ecd375d0..14e72ae3 100644 --- a/example/ios/Podfile.lock +++ b/example/ios/Podfile.lock @@ -1268,7 +1268,7 @@ PODS: - ReactCommon/turbomodule/core - ReactNativeDependencies - Yoga - - react-native-safe-area-context (5.9.0): + - react-native-safe-area-context (5.9.1): - hermes-engine - RCTRequired - RCTTypeSafety @@ -1281,8 +1281,8 @@ PODS: - React-graphics - React-ImageManager - React-jsi - - react-native-safe-area-context/common (= 5.9.0) - - react-native-safe-area-context/fabric (= 5.9.0) + - react-native-safe-area-context/common (= 5.9.1) + - react-native-safe-area-context/fabric (= 5.9.1) - React-NativeModulesApple - React-RCTFabric - React-renderercss @@ -1292,7 +1292,7 @@ PODS: - ReactCommon/turbomodule/core - ReactNativeDependencies - Yoga - - react-native-safe-area-context/common (5.9.0): + - react-native-safe-area-context/common (5.9.1): - hermes-engine - RCTRequired - RCTTypeSafety @@ -1314,7 +1314,7 @@ PODS: - ReactCommon/turbomodule/core - ReactNativeDependencies - Yoga - - react-native-safe-area-context/fabric (5.9.0): + - react-native-safe-area-context/fabric (5.9.1): - hermes-engine - RCTRequired - RCTTypeSafety @@ -2128,7 +2128,7 @@ SPEC CHECKSUMS: React-Mapbuffer: acf4ac61f163f15ced7dfad7308957816b2d7abd React-microtasksnativemodule: 512d9f7c6b66574d90832a6b10b6102d4a8fdf30 React-mutationobservernativemodule: 2c5abeb9a4ae316ba6d9420ef8d9baa81faa9d56 - react-native-safe-area-context: 582cd62c1264dccf5fd9fab929d18bfed0391f5c + react-native-safe-area-context: 43b1d80b9c1b48e0f26518bfd4e7ffbc992e69b1 React-NativeModulesApple: 22b2f3e1538ceb1aab1ab182ccb0666ea2ec36ad React-networking: b58b3098d4a626f88bbaeaf6bf5e67b18ff39089 React-oscompat: 72573ceb65b6c6c6bc34e51e0df8f44c91081a6d