Skip to content

Commit

Permalink
RJS-2417: Migrating our RN test app to "React Native Test App" (#6570)
Browse files Browse the repository at this point in the history
* Initial commit with RNTA

* Updating node_modules paths

* Ran an install

* Comitting in the Podfile.lock

* Adding a tsconfig.json to RNTA environment

* Using TS project references in integration tests

* Upgrading mocha-remote

* Removing the old RN test app

* Adding a RNTA environment

* Switching PR workflow to use the new app

* Adding missing npm scripts

* Adding "--" to mocha-remote calls

* Avoiding "type": "module" as it breaks node-tests

* The new Mocha client injects context into the context, so we need to rename "longTimeout"

* Using "*" as range for "realm" and

* Upgrading realm-web-integration-tests deps and mocha-remote across

* Updating realm-web-integration-tests harness

* Adding missing header to config files

* Upgrading mocha-remote

* Moving bundled Realm into app directory

* Building android instead of pod-install

* Passing gradle project settings via wireit

* Upgrading RN to 0.73.6

* Ensure useDefineForClassFields is disabled when running tests via tsx and mocha

* Adding a base-path to fix the "coveralls" GHA invocation

* Renamed longTimeout to longTimeoutMs in coverage workflow

* Removed the base-path from coveralls action

* Apply suggestions from code review

Co-authored-by: LJ <81748770+elle-j@users.noreply.github.com>

---------

Co-authored-by: LJ <81748770+elle-j@users.noreply.github.com>
  • Loading branch information
kraenhansen and elle-j authored Apr 4, 2024
1 parent 40e4801 commit 4ada449
Show file tree
Hide file tree
Showing 96 changed files with 5,567 additions and 5,454 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/pr-coverage.yml
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ jobs:
timeout-minutes: 60
run: npm run ci:coverage --workspace @realm/integration-tests -- --reporter mocha-github-actions-reporter --timeout ${{ env.MOCHA_TIMEOUT }}
env:
CONTEXT: syncLogLevel=warn,longTimeout=${{ env.LONG_TIMEOUT }},baseUrl=${{ steps.baas.outputs.baas-url }}
CONTEXT: syncLogLevel=warn,longTimeoutMs=${{ env.LONG_TIMEOUT }},baseUrl=${{ steps.baas.outputs.baas-url }}

- name: Coveralls
uses: coverallsapp/github-action@v2
14 changes: 7 additions & 7 deletions .github/workflows/pr-realm-js.yml
Original file line number Diff line number Diff line change
Expand Up @@ -272,9 +272,9 @@ jobs:
- { os: darwin, target: "test:ci:main", runner: macos-latest, environment: electron }
- { os: darwin, target: "test:ci:renderer", runner: macos-latest, environment: electron }
- { os: darwin, target: "test:ci", runner: macos-latest, environment: node }
- { os: android, target: "test:ci:android", runner: macos-latest-large, environment: react-native, arch: "armeabi-v7a" }
- { os: ios, target: "test:ci:ios", runner: macos-latest-xlarge, environment: react-native, arch: "ios" }
#- { os: ios, target: "test:ci:catalyst", runner: macos-latest, environment: react-native, arch: "catalyst" }
- { os: android, target: "test:ci:android", runner: macos-latest-large, environment: react-native-test-app, arch: "armeabi-v7a" }
- { os: ios, target: "test:ci:ios", runner: macos-latest-xlarge, environment: react-native-test-app, arch: "ios" }
#- { os: ios, target: "test:ci:catalyst", runner: macos-latest, environment: react-native-test-app, arch: "catalyst" }
timeout-minutes: 60
steps:
- name: Checkout code
Expand Down Expand Up @@ -306,7 +306,7 @@ jobs:
uses: google/wireit@setup-github-actions-caching/v1

- name: Restore React Native cache
if: ${{ matrix.variant.environment == 'react-native' }}
if: ${{ matrix.variant.environment == 'react-native-test-app' }}
uses: actions/cache@v3
with:
path: '**/Pods'
Expand All @@ -320,15 +320,15 @@ jobs:

- name: ccache
uses: hendrikmuhs/ccache-action@v1
if: ${{ matrix.variant.environment == 'react-native' }}
if: ${{ matrix.variant.environment == 'react-native-test-app' }}
with:
key: ${{ runner.os }}-${{ matrix.variant.os }}-${{ matrix.variant.arch }}
max-size: '2.0G'

# in CI file timestamps change with every run so instead rely on file content hashing
# https://reactnative.dev/docs/build-speed#using-this-approach-on-a-ci
- name: Configure ccache
if: ${{ matrix.variant.environment == 'react-native' }}
if: ${{ matrix.variant.environment == 'react-native-test-app' }}
run: ccache --set-config="compiler_check=content"

# Hermes doesn't work with Cocoapods 1.15.0
Expand Down Expand Up @@ -385,7 +385,7 @@ jobs:

- name: Create Mocha Remote Context
id: mocha-env
run: echo "context=syncLogLevel=warn,longTimeout=${{ env.LONG_TIMEOUT }},baseUrl=${{ steps.baas.outputs.baas-url }}" >> $GITHUB_OUTPUT
run: echo "context=syncLogLevel=warn,longTimeoutMs=${{ env.LONG_TIMEOUT }},baseUrl=${{ steps.baas.outputs.baas-url }}" >> $GITHUB_OUTPUT

- name: Run ${{matrix.variant.target}} (${{ matrix.variant.os}} / ${{ matrix.variant.environment }})
if: ${{ matrix.variant.os != 'android' && matrix.variant.os != 'ios' }}
Expand Down
12 changes: 6 additions & 6 deletions integration-tests/environments/electron/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,8 @@
"test": "wireit",
"test:main": "wireit",
"test:renderer": "wireit",
"test:ci:main": "mocha-remote --reporter mocha-github-actions-reporter --id main tsx runner.ts main",
"test:ci:renderer": "mocha-remote --reporter mocha-github-actions-reporter --id renderer tsx runner.ts renderer",
"test:ci:main": "mocha-remote --reporter mocha-github-actions-reporter --id main -- tsx runner.ts main",
"test:ci:renderer": "mocha-remote --reporter mocha-github-actions-reporter --id renderer -- tsx runner.ts renderer",
"lint": "eslint .",
"package": "electron-builder --dir"
},
Expand All @@ -23,15 +23,15 @@
"command": "npm run test:main && npm run test:renderer"
},
"test:main": {
"command": "mocha-remote --reporter @realm/mocha-reporter --id main tsx runner.ts main",
"command": "mocha-remote --reporter @realm/mocha-reporter --id main -- tsx runner.ts main",
"dependencies": [
"../../../packages/realm:build:ts",
"../../../packages/realm:build:node",
"../../../packages/mocha-reporter:bundle"
]
},
"test:renderer": {
"command": "mocha-remote --reporter @realm/mocha-reporter --id renderer tsx runner.ts renderer",
"command": "mocha-remote --reporter @realm/mocha-reporter --id renderer -- tsx runner.ts renderer",
"dependencies": [
"../../../packages/realm:build:ts",
"../../../packages/realm:build:node",
Expand All @@ -46,13 +46,13 @@
"electron-builder": "^24.9.1",
"mocha-github-actions-reporter": "^0.3.0",
"mocha-junit-reporter": "^2.2.0",
"mocha-remote-cli": "^1.8.0"
"mocha-remote-cli": "^1.12.2"
},
"dependencies": {
"@electron/remote": "^2.1.2",
"@realm/integration-tests": "*",
"fs-extra": "^11.2.0",
"mocha-remote-client": "^1.8.0",
"mocha-remote-client": "^1.12.2",
"@realm/app-importer": "*"
},
"build": {
Expand Down
10 changes: 5 additions & 5 deletions integration-tests/environments/node/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,20 +6,20 @@
"scripts": {
"test": "wireit",
"test:commonjs": "wireit",
"test:ci": "mocha-remote --reporter @realm/mocha-reporter tsx index.mjs",
"test:ci": "mocha-remote --reporter @realm/mocha-reporter -- tsx index.mjs",
"lint": "eslint --ext js,mjs ."
},
"wireit": {
"test": {
"command": "mocha-remote --reporter @realm/mocha-reporter tsx index.mjs",
"command": "mocha-remote --reporter @realm/mocha-reporter -- tsx index.mjs",
"dependencies": [
"../../../packages/realm:build:ts",
"../../../packages/realm:build:node",
"../../../packages/mocha-reporter:bundle"
]
},
"test:commonjs": {
"command": "mocha-remote --reporter @realm/mocha-reporter tsx index.cjs",
"command": "mocha-remote --reporter @realm/mocha-reporter -- tsx index.cjs",
"dependencies": [
"../../../packages/realm:build:ts",
"../../../packages/realm:build:node",
Expand All @@ -30,8 +30,8 @@
"dependencies": {
"@realm/integration-tests": "*",
"mocha-github-actions-reporter": "^0.3.1",
"mocha-remote-cli": "^1.8.0",
"mocha-remote-client": "^1.8.0",
"mocha-remote-cli": "^1.12.2",
"mocha-remote-client": "^1.12.2",
"realm": "*"
},
"devDependencies": {
Expand Down
16 changes: 16 additions & 0 deletions integration-tests/environments/react-native-test-app/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
*.binlog
*.hprof
*.xcworkspace/
*.zip
.DS_Store
.gradle/
.idea/
.vs/
.xcode.env
Pods/
build/
dist/*
!dist/.gitignore
local.properties
msbuild.binlog
node_modules/
102 changes: 102 additions & 0 deletions integration-tests/environments/react-native-test-app/App.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
////////////////////////////////////////////////////////////////////////////
//
// Copyright 2024 Realm Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
////////////////////////////////////////////////////////////////////////////
import React from "react";
import { StyleSheet, View, SafeAreaView, StatusBar, Platform } from "react-native";

import { MochaRemoteProvider, ConnectionText, StatusEmoji, StatusText, CustomContext } from "mocha-remote-react-native";

// Registering an error handler that always throw unhandled exceptions
// This is to enable the remote-mocha-cli to exit on uncaught errors
const originalHandler = ErrorUtils.getGlobalHandler();
ErrorUtils.setGlobalHandler((err, isFatal) => {
// Calling the original handler to show the error visually too
originalHandler(err, isFatal);
throw err;
});

function loadTests(context: CustomContext) {
/* eslint-env mocha */
// Quick sanity check that "realm" is loadable at all
require("realm");
/* eslint-disable-next-line no-restricted-globals */
Object.assign(globalThis, {
fs: require("react-native-fs"),
path: require("path-browserify"),
environment: {
// Default to the host machine when running on Android
baseUrl: Platform.OS === "android" ? "http://10.0.2.2:9090" : undefined,
...context,
// TODO: Incorporate this into the Mocha context instead
reactNative: Platform.OS,
android: Platform.OS === "android",
ios: Platform.OS === "ios",
},
});
// Make the tests reinitializable, to allow test running on changes to the "realm" package
// Probing the existance of `getModules` as this only exists in debug mode
// if ("getModules" in require) {
// const modules = require.getModules();
// for (const [, m] of Object.entries(modules)) {
// if (m.verboseName.startsWith("../../tests/")) {
// m.isInitialized = false;
// }
// }
// }
// Require in the integration tests
require("@realm/integration-tests");
}

export default function App() {
return (
<MochaRemoteProvider tests={loadTests}>
<StatusBar hidden />
<SafeAreaView style={styles.container}>
<ConnectionText style={styles.connectionText} />
<View style={styles.statusContainer}>
<StatusEmoji style={styles.statusEmoji} />
<StatusText style={styles.statusText} />
</View>
</SafeAreaView>
</MochaRemoteProvider>
);
}

const styles = StyleSheet.create({
container: {
flex: 1,
backgroundColor: "#fff",
},
statusContainer: {
flex: 1,
alignItems: "center",
justifyContent: "center",
},
statusEmoji: {
fontSize: 30,
margin: 30,
textAlign: "center",
},
statusText: {
fontSize: 20,
margin: 20,
textAlign: "center",
},
connectionText: {
textAlign: "center",
},
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
buildscript {
def androidTestAppDir = "../../../../node_modules/react-native-test-app/android"
apply(from: "${androidTestAppDir}/dependencies.gradle")

repositories {
mavenCentral()
google()
}

dependencies {
getReactNativeDependencies().each { dependency ->
classpath(dependency)
}
}
}

allprojects {
repositories {
maven {
// All of React Native (JS, Obj-C sources, Android binaries) is installed from npm
url("../../../../node_modules/react-native/android")
}
mavenCentral()
google()
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,22 +7,27 @@
# For more details on how to configure your build environment visit
# http://www.gradle.org/docs/current/userguide/build_environment.html

# 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=-Xmx4608m -XX:MaxMetaspaceSize=512m

# 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
# Specifies the JVM arguments used for the Gradle Daemon. The setting is
# particularly useful for configuring JVM memory settings for build performance.
# This does not affect the JVM settings for the Gradle client VM.
# The default is `-Xmx512m -XX:MaxMetaspaceSize=256m`.
org.gradle.jvmargs=-Xmx2g -XX:MaxMetaspaceSize=512m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8

# When configured, Gradle will fork up to org.gradle.workers.max JVMs to execute
# projects in parallel. To learn more about parallel task execution, see the
# section on Gradle build performance:
# https://docs.gradle.org/current/userguide/performance.html#parallel_execution.
# Default is `false`.
#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
# Automatically convert third-party libraries to use AndroidX
android.enableJetifier=true
# Jetifier randomly fails on these libraries
android.jetifier.ignorelist=hermes-android

# Use this property to specify which architecture you want to build.
# You can also override it from the CLI using
Expand All @@ -34,8 +39,15 @@ reactNativeArchitectures=armeabi-v7a,arm64-v8a,x86,x86_64
# 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=false
# Note that this is incompatible with web debugging.
#newArchEnabled=true
#bridgelessEnabled=true

# Uncomment the line below to build React Native from source.
#react.buildFromSource=true

# Version of Android NDK to build against.
#ANDROID_NDK_VERSION=26.1.10909125

# Use this property to enable or disable the Hermes JS engine.
# If set to false, you will be using JSC instead.
hermesEnabled=true
# Version of Kotlin to build against.
#KOTLIN_VERSION=1.8.22
Binary file not shown.
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.3-all.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-8.6-bin.zip
networkTimeout=10000
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -145,15 +145,15 @@ if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then
case $MAX_FD in #(
max*)
# In POSIX sh, ulimit -H is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC3045
# shellcheck disable=SC2039,SC3045
MAX_FD=$( ulimit -H -n ) ||
warn "Could not query maximum file descriptor limit"
esac
case $MAX_FD in #(
'' | soft) :;; #(
*)
# In POSIX sh, ulimit -n is undefined. That's why the result is checked to see if it worked.
# shellcheck disable=SC3045
# shellcheck disable=SC2039,SC3045
ulimit -n "$MAX_FD" ||
warn "Could not set maximum file descriptor limit to $MAX_FD"
esac
Expand Down Expand Up @@ -202,11 +202,11 @@ fi
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'

# Collect all arguments for the java command;
# * $DEFAULT_JVM_OPTS, $JAVA_OPTS, and $GRADLE_OPTS can contain fragments of
# shell script including quotes and variable substitutions, so put them in
# double quotes to make sure that they get re-expanded; and
# * put everything else in single quotes, so that it's not re-expanded.
# Collect all arguments for the java command:
# * DEFAULT_JVM_OPTS, JAVA_OPTS, JAVA_OPTS, and optsEnvironmentVar are not allowed to contain shell fragments,
# and any embedded shellness will be escaped.
# * For example: A user cannot expect ${Hostname} to be expanded, as it is an environment variable and will be
# treated as '${Hostname}' itself on the command line.

set -- \
"-Dorg.gradle.appname=$APP_BASE_NAME" \
Expand Down
Loading

0 comments on commit 4ada449

Please sign in to comment.