Compare commits

..
54 Commits
Author SHA1 Message Date
React Native Bot 06c4c425d7 Release 0.82.0
#publish-packages-to-npm&latest
2025-10-07 22:17:26 +00:00
React Native Bot 8677203b7a [LOCAL] Bump Podfile.lock 2025-09-30 13:20:51 +00:00
React Native Bot 3336199242 Release 0.82.0-rc.5
#publish-packages-to-npm&next
2025-09-30 11:07:35 +00:00
Tim YungandVitali Zaidman fddf263dbc RN: Deprecate InteractionManager (#53832)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53832

Deprecates `InteractionManager` by adding a warning when it is imported.

Changelog:
[General][Changed] - InteractionManager has been deprecated and no longer respects interaction handles. Instead, it is now recommended to avoid executing long-running JavaScript tasks by breaking them up into smaller tasks and scheduling them using `requestIdleCallback()`.

Reviewed By: javache

Differential Revision: D82704809

fbshipit-source-id: 99474cd7949abfe323c366b9ab8d8fc195578395
2025-09-29 14:58:02 +01:00
Tim YungandVitali Zaidman 458cd06bdb RN: Remove References to InteractionManager (#53830)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53830

Now that `InteractionManager` is deprecated (and no-ops), this removes all remaining references to it — in `Animated` and `PanResponder` — from the React Native repository.

Changelog:
[Internal]

Reviewed By: javache

Differential Revision: D82690242

fbshipit-source-id: d101d47d1f8640f70e2d199492d4345b63663251
2025-09-29 14:55:13 +01:00
Riccardo CipolleschiandVitali Zaidman e5fca6c363 Crash the app when Legacy Arch is enabled (#53911)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53911

This change mimics what we implemented on Android to crash the app.

This is in general never going t be triggered. It will be triggered only if users are actually going through the old way to initialize React Native, i.e. by using the RCTRootView class which creates thebridge, or if they are creating the bridge themselves.

## Changelog:
[iOS][Added] - Crash the app if they force the legacy architecture.

Reviewed By: RSNara, cortinico

Differential Revision: D83066377

fbshipit-source-id: 0907effceb9a3655ec8d6bde8e0986f50f1ab663
2025-09-29 14:54:43 +01:00
Kacper KafaraandVitali Zaidman b1994dd547 Add invalidation callback for non-recycled component instances on iOS (#53708)
Summary:
Since the view recycling is optional on iOS [since 0.74](https://github.com/facebook/react-native/commit/613a5a75977d84333df7cbd5701e01a7ab5a3385) when a view (with disabled view recycling) is unmounted / destroyed there is no lifecycle callback for a component view to notify it of such event. Currently we (`react-native-screens`) are forced to scan mutation list of every mounting transaction in every of ours container components. Components with view recycling turned on, get `prepareForRecycle` callback on Fabric & on old architecture, there was `invalidate` message sent (`RCTInvalidating` protocol). It would be nice & useful to have something like this for components with view recycling disabled, or enabled but not recycled due to pool being full.

In particular in `react-native-screens` we need an information that the component is being destroyed to release retained resources (view controllers & others).

I have concern regarding naming of this method, as it could collide / be mistaken with `invalidate` method of `RCTInvalidating` protocol, but naming is hard & I don't see a name that fits better 😄 Open for suggestions!

## Changelog:

<!-- Help reviewers and the release process by writing your own changelog entry.

Pick one each for the category and type tags:

[ANDROID|GENERAL|IOS|INTERNAL] [BREAKING|ADDED|CHANGED|DEPRECATED|REMOVED|FIXED|SECURITY] - Message

For more details, see:
https://reactnative.dev/contributing/changelogs-in-pull-requests
-->

[IOS] [ADDED] - Add invalidation callback for non-recycled component instances

Pull Request resolved: https://github.com/facebook/react-native/pull/53708

Test Plan:
Apply this patch to `RNTMyNativeViewComponentView.mm`:

```objective-c

 diff --git a/packages/rn-tester/NativeComponentExample/ios/RNTMyNativeViewComponentView.mm b/packages/rn-tester/NativeComponentExample/ios/RNTMyNativeViewComponentView.mm
index 2eb7bff28e..8464da603b 100644
 --- a/packages/rn-tester/NativeComponentExample/ios/RNTMyNativeViewComponentView.mm
+++ b/packages/rn-tester/NativeComponentExample/ios/RNTMyNativeViewComponentView.mm
@@ -123,6 +123,16 @@ using namespace facebook::react;
   [_view removeOverlays];
 }

+- (void)invalidate
+{
+  NSLog(@"RCTComponentViewProtocol invalidate called");
+}
+
++ (BOOL)shouldBeRecycled
+{
+  return NO;
+}
+
 - (void)fireLagacyStyleEvent
 {
   RNTMyNativeViewEventEmitter::OnLegacyStyleEvent value = {"Legacy Style Event Fired."};

```

& render `MyNativeView` in any of the RNTester screens / examples. Unmount the view & observe the log in XCode.

https://github.com/user-attachments/assets/be3f67bb-73e0-4af2-9ca1-f2eb9f3347bb

(called twice, because there are two components rendered at a time)

Reviewed By: javache

Differential Revision: D83139361

Pulled By: cipolleschi

fbshipit-source-id: 17ef964648ac44b583503b6b00fc5dd457887061
2025-09-29 14:54:21 +01:00
Jakub PiaseckiandGitHub 6efaeaf953 [0.82] Update Hermes V1 version (#53932)
* Update hermes V1 version

* Pin Hermes V1 source version to a specific commit
2025-09-29 14:52:37 +01:00
React Native Bot 0dd3730d23 [LOCAL] Bump Podfile.lock 2025-09-22 17:44:42 +00:00
React Native Bot a70e817da5 Release 0.82.0-rc.4
#publish-packages-to-npm&next
2025-09-22 15:19:10 +00:00
Riccardo CipolleschiandVitali Zaidman 9f43d07679 Fix Switch layout with iOS26 (#53326)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53326

Apple changed the sizes of the UISwitchComponent and now, if you build an iOs app using the <Switch> component, the layout of the app will be broken because of wrong layout measurements.
This has been reported also by [https://github.com/facebook/react-native/issues/52823](https://github.com/facebook/react-native/issues/52823).

The `<Switch>` component was using hardcoded values for its size.
This change fixes the problem by:
- Using codegen for interface only
- Implementing a custom Sadow Node to ask the platform for the Switch measurements
- Updating the JS layout to wrap the size around the native component.

## Changelog:

[iOS][Fixed] - Fix Switch layout to work with iOS26

Reviewed By: sammy-SC

Differential Revision: D80454350

fbshipit-source-id: 1d468910276f7fde4559d2ae87cf60c8494caceb
2025-09-22 14:34:29 +01:00
Jakub PiaseckiandVitali Zaidman 8d775928f5 Update coordinates for remote artifacts of Hermes V1 (#53822)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53822

Changelog: [GENERAL][FIXED] - Fixed coordinates for Hermes V1 artifacts

Reviewed By: cortinico

Differential Revision: D82639319

fbshipit-source-id: becfab3248f2314af97549eb94feb27b19f5d1af
2025-09-22 14:34:01 +01:00
8dddde49b2 [0.82] Ensure legacy architecture can't be initialized (#53843)
* Ensure legacy architecture can't be initialized in Android (#53806)

Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53806

The Legacy architecture of React Native is not supported anymore, let's ensure nobody can initialize it anymore

changelog: [internal] internal

Reviewed By: cortinico

Differential Revision: D82465004

fbshipit-source-id: 099764fb59d906b11cf6ad0cc6208f56df029d19

* Runtime check that NewArchitecture is enabled in DefaultNewArchitectureEntryPoint (#53780)

Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53780

This is a commit we're going to pick in 0.82 as we want to make sure users cannot invoke `load()`
from `DefaultNewArchitectureEntryPoint` with flags that are not true,true,true.

Changelog:
[Android] [Changed] - Runtime check that NewArchitecture is enabled in DefaultNewArchitectureEntryPoint

Reviewed By: mdvacca

Differential Revision: D82456975

fbshipit-source-id: 749996a3491913cfe400173608218077c3ffbc10

* Fix DefaultNewArchitectureEntryPoint config validation (#53807)

Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53807

We need to read the values off feature flags before checking them.

## Changelog
[Internal]

Reviewed By: javache

Differential Revision: D82572898

fbshipit-source-id: 09fbc09570c78b41d9c25fb03c5557e390da7cae

* Fix incorrect validation of feature flags in DefaultNewArchitectureEntryPoint.loadWithFeatureFlags() method (#53863)

Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53863

In this diff I'm fixing an incorrect validation of feature flags in DefaultNewArchitectureEntryPoint.loadWithFeatureFlags() method.

changelog: [internal] internal

Reviewed By: cortinico

Differential Revision: D82841006

fbshipit-source-id: 6f50f2475255d7b841d9224bc8808119dcc68aec

---------

Co-authored-by: David Vacca <dvacca@meta.com>
Co-authored-by: Eric Rozell <ericroz@meta.com>
2025-09-22 14:24:33 +01:00
React Native Bot 3a0a7365ff [LOCAL] Bump Podfile.lock 2025-09-17 09:41:27 +00:00
React Native Bot 45439b0119 Release 0.82.0-rc.3
#publish-packages-to-npm&next
2025-09-17 07:27:43 +00:00
React Native Bot 16bc2e4569 Release 0.82.0-rc.2
#publish-packages-to-npm&next
2025-09-16 13:12:26 +00:00
Vitali Zaidman 47c04b9930 [LOCAL] remove faulty cherry pick networking lines from Android's CMakeList.txt 2025-09-16 11:43:26 +01:00
Rubén NorteandVitali Zaidman 1a0f7b26bc Ship Web Performance APIs in canary (#53712)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53712

Changelog: [internal]

This enables the new Web Performance APIs in the canary channel.

Reviewed By: cortinico

Differential Revision: D82117694

fbshipit-source-id: 370b8397eeec350be8434728ab9d8ce1f5926117
2025-09-16 11:25:30 +01:00
Rubén NorteandVitali Zaidman bf9c6514fc Remove redudant fields from ReactNativeStartupTiming (#53711)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53711

Changelog: [internal]

This removes some fields that contain the same time as `endTime`, which is confusing when documenting them.

Reviewed By: christophpurrer

Differential Revision: D82112473

fbshipit-source-id: 461e2b4b495ae641dcb3233874360a4f7b90dabf
2025-09-16 11:25:14 +01:00
Rubén NorteandVitali Zaidman 5f1a22ac8d Make eventCounts a getter (#53710)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53710

Changelog: [internal]

This should be a getter according to the spec.

Reviewed By: hoxyq

Differential Revision: D82111779

fbshipit-source-id: 614bb4848907bacd80ef228aa747ae685cf2c1f7
2025-09-16 11:25:01 +01:00
Rubén NorteandVitali Zaidman e8129c37d9 Implement performance.timeOrigin (#53660)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53660

Changelog: [internal]

(This is internal because these APIs aren't enabled in OSS yet)

Implements `performance.timeOrigin` to allow converting timestamps from `performance.now()` to be based on the Unix epoch.

This implementation isn't fully spec-compliant to align with the current implementation of `performance.now()`, where the base of the clock is system boot time instead of app startup / navigation time.

Reviewed By: huntie

Differential Revision: D82016724

fbshipit-source-id: e3a066721cecf41e2fd963beb94a0a2f1c5d6493
2025-09-16 11:24:50 +01:00
Rubén NorteandVitali Zaidman e6d1ab8c66 Add feature flag to enable Web Performance APIs by default (#53547)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53547

Changelog: [internal]

This creates a new feature flag to enable the modern Web performance APIs in RN by default. It's disabled by default so it shouldn't have any effect at the moment.

Reviewed By: rshest

Differential Revision: D80811430

fbshipit-source-id: 47d5fd12ac8809aa3c5ad37cdd31c0d9e3ed5912
2025-09-16 11:23:31 +01:00
Nicola CortiandVitali Zaidman e87a8820a5 Unblock run_fantom_tests by pinning react-native-android to v18.0 (#53732)
Summary:
This temporarly unblocks `run_fantom_tests` till we find a solution for the docker image bump. See:
- https://github.com/react-native-community/docker-android/pull/242#issuecomment-3280029122

## Changelog:

[INTERNAL] -

Pull Request resolved: https://github.com/facebook/react-native/pull/53732

Test Plan: CI

Reviewed By: cipolleschi

Differential Revision: D82212022

Pulled By: cortinico

fbshipit-source-id: 652926addf12cc2d88ac2139d3ec58a266ced9ef
2025-09-16 11:04:18 +01:00
Vitali Zaidman 736f608364 re-generated feature flag generated files 2025-09-16 10:30:20 +01:00
Jakub PiaseckiandVitali Zaidman 4c8b6a6915 Add dependency on hermes-compiler (#53773)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53773

Changelog: [GENERAL][ADDED] - Added a dependency on hermes-compiler

Reviewed By: cortinico

Differential Revision: D82437752

fbshipit-source-id: 3b2d92b765f3a5ba949363ce7656e936403a1155
2025-09-15 14:40:21 +01:00
Rubén NorteandVitali Zaidman 06ab1f446c Ship Web Performance APIs in canary (#53712)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53712

Changelog: [internal]

This enables the new Web Performance APIs in the canary channel.

Reviewed By: cortinico

Differential Revision: D82117694

fbshipit-source-id: 370b8397eeec350be8434728ab9d8ce1f5926117
2025-09-15 14:35:12 +01:00
Phil PluckthunandVitali Zaidman 7754c05db4 Remove outdated artifacts codegen early return (#53690)
Summary:
Follow-up to https://github.com/facebook/react-native/issues/53503 for a regression

When no React Native module is present this bail condition stops us from generating the artifacts podspec that's needed to complete build.

## Changelog:

[IOS] [FIXED] - Fix regression that skips artifacts code generation

Pull Request resolved: https://github.com/facebook/react-native/pull/53690

Test Plan:
- Create an app **without** any React Native modules, run `pod install`; without this fix the podspec will be missing and the build will fail
  - With expo this can be reproduced using `create-expo-app --template blank-typescript@next` on `react-native@0.81.2`
  - With the community CLI this can be reproduced using `npx react-native-community/cli@latest init test --skip-install --version 0.81.2` and uninstalling `react-native-safe-area-context`

Reviewed By: javache

Differential Revision: D82103491

Pulled By: cipolleschi

fbshipit-source-id: 3d9619b5a935ca920220824b3963a9a107f926ca
2025-09-15 14:32:49 +01:00
Jakub PiaseckiandGitHub 4c53204422 [0.82] Cherry-pick follow-ups to Hermes V1 opt-in (#53705)
* Check value of the Hermes V1 flag instead of whether it's defined (#53637)

Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53637

Changelog: [ANDROID][FIXED] - Check for the value of the HERMES_V1_ENABLED flag instead of whether it's defined

Reviewed By: cortinico

Differential Revision: D81920483

fbshipit-source-id: 550ae9fd27f666affe102b1c5c3f51bde7b5923e

* Read Hermes V1 opt-in flag from the app's properties (#53665)

Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53665

Changelog: [ANDROID][FIXED] - Read the Hermes V1 opt-in flag from the apps properties when building from source

Reviewed By: cortinico

Differential Revision: D82018545

fbshipit-source-id: f3c6fdbac190f47b6bf6836105d9e0909d8b86ba

* Use artifacts published from Hermes repository when using Hermes V1 (#53725)

Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53725

Changelog: [GENERAL][CHANGED] - Changed the coordinates of hermes artifacts when using Hermes V1

Adds a new `version.properties` file to keep which hermes versions should be consumed from Maven once the versions of Hermes and React Native are decoupled. This diff only implements changes necessary for consuming Hermes V1, as we don't want to migrate everything quite yet (0.82).

Reviewed By: cortinico

Differential Revision: D82204203

fbshipit-source-id: d712257a73f7ba54612a55c1b312416376f28b56
2025-09-15 14:31:05 +01:00
Nicola Corti 71c853ca6d [LOCAL] Use REACT_NATIVE_BOT_GITHUB_TOKEN token for changelog and bump lockfiles 2025-09-09 15:30:28 +01:00
Vitali Zaidman 788e2b9d62 Update Podfile.lock
Changelog: [Internal]
2025-09-09 14:10:55 +01:00
React Native Bot 3c2cc3852d Release 0.82.0-rc.1
#publish-packages-to-npm&next
2025-09-09 10:02:01 +00:00
Nicola Corti f68b918c89 [LOCAL] Remove unnecesary quote in hermesVersionProvider 2025-09-08 15:51:35 +01:00
Nicola Corti ee08261123 [LOCAL] Temporarily disable prebuilds for 0.82 branch 2025-09-08 15:40:05 +01:00
Rubén NorteandVitali Zaidman ac2fe26cf2 Define Flow types for Performance APIs (#53433)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53433

Changelog: [internal]

This adds the definitions for the Web Performance APIs in the global scope.

Reviewed By: zeyap

Differential Revision: D80811659

fbshipit-source-id: a81117a27a480ba03f8feb2e813a3a66a10307f9
2025-09-08 14:56:46 +01:00
Rubén NorteandVitali Zaidman cdfe1ecd52 Set up modern performance APIs if the native module is available (#53431)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53431

Changelog: [internal]

This renames `setUpPerformanceObserver` as `setUpPerformanceModern` and removes the need to call it manually. If the native module is defined, we define the whole new API.

Reviewed By: javache

Differential Revision: D80803626

fbshipit-source-id: ef41cb9aa959ee898d32724c102d7597e6bee84e
2025-09-08 14:44:39 +01:00
Rubén NorteandVitali Zaidman a65325b586 Implement private constructors for Performance APIs (#53430)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53430

Changelog: [internal]

This fixes the spec-compliance of several classes in the Performance API by not allowing userland code to instantiate them directly.

This also exposes some missing interfaces from the Performance API in the global scope.

Reviewed By: rshest

Differential Revision: D80800076

fbshipit-source-id: f6439b9c7914817ef552e78fd61646ccab1e1de2
2025-09-08 14:44:27 +01:00
Rubén NorteandVitali Zaidman ccb34a1063 Refactor PerformanceEntry and subclasses to use interfaces for initialization (#53429)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53429

Changelog: [internal]

This is a refactor of the types in `PerformanceEntry` and subclasses to accept interfaces instead of objects. This allows us to pass down the init object from subclasses to the superclass without having to create intermediate objects.

Additionally, this is also more semantically correct, as existing APIs don't need those options to be own properties of the init object.

Existing benchmark for Performance doesn't show any significant impact.

Reviewed By: rshest

Differential Revision: D80800075

fbshipit-source-id: ab439d70f4db9ce60e3089d89ccb105a91e7ef48
2025-09-08 14:44:14 +01:00
Rubén NorteandVitali Zaidman 68e774bb2c Implement PerformanceObserver.takeRecords() (#53428)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53428

Changelog: [internal]

This is the last method in `PerformanceObserver` to implement. For some reason we never added it, even though it was trivial.

Reviewed By: rshest

Differential Revision: D80717237

fbshipit-source-id: ae3bd243d0f3f0fe4f0705437d78d14c532515f7
2025-09-08 14:43:50 +01:00
Rubén NorteandVitali Zaidman 1cacdf70a1 Remove unnecessary references to internal types in performance tests (#53427)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53427

Changelog: [internal]

Migrate the imported types to the globally defined ones, so we follow the good practice of only accessing the public API in Fantom tests.

Reviewed By: rshest

Differential Revision: D80807160

fbshipit-source-id: 77d792b56b53c8da8409dd9133cd111afb8084f1
2025-09-08 14:41:23 +01:00
Ramanpreet NaraandVitali Zaidman 72d4a1cbd4 Deprecate legacy javascript apis (#53630)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53630

These JavaScript apis were a part of react native's legacy architecture. Let's deprecate them, so that we can eventually remove them in the future.

Changelog: [General][Deprecated] - Deprecate legacy javascript react native apis

Reviewed By: cortinico

Differential Revision: D81795732

fbshipit-source-id: 0a2bd142fa7e08c1f3daaa437ee127a2156e045b
2025-09-08 14:39:28 +01:00
Oskar KwaśniewskiandVitali Zaidman 0cfd7230c6 fix: fallback alert controller to UIScreen size (#53500)
Summary:
This PR falls back to UIScreen when windowScene is not available.

<img width="500" alt="CleanShot 2025-08-28 at 14 30 59@2x" src="https://github.com/user-attachments/assets/9dda3153-dfe7-48a5-9d0e-5416c2e34c64" />

## Changelog:

[IOS] [FIXED] - Simplify RCTAlertController, don't create additional UIWindow

Pull Request resolved: https://github.com/facebook/react-native/pull/53500

Test Plan:
Open the alert multiple times to check if everything works as expected.

Rollback Plan:

Reviewed By: javache

Differential Revision: D81410450

Pulled By: cipolleschi

fbshipit-source-id: c27ea98d9e811c2f259f0ff3c6689482d116c418
2025-09-08 14:39:03 +01:00
Jakub PiaseckiandVitali Zaidman 4fdefa7193 Use hermesc from node_modules when consuming prebuilt hermes (#53581)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53581

Changelog: [General][Changed] - Changed the source of hermesc binary to be an npm package

Reviewed By: cipolleschi, cortinico

Differential Revision: D81224001

fbshipit-source-id: 552d0e66fb891974d7b688bfc0bec95e19345d86
2025-09-08 14:38:24 +01:00
Jakub PiaseckiandVitali Zaidman af734f0ccd Allow to opt-in to use the new Hermes on Android (#53580)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53580

Changelog: [ANDROID][ADDED] Added opt-in to use the new Hermes

Reviewed By: cortinico

Differential Revision: D81035114

fbshipit-source-id: d01e44190941d161cf641ec4e03ed487aff18dd8
2025-09-08 14:38:09 +01:00
Jakub PiaseckiandVitali Zaidman af090eaa69 Allow to opt-in to use the new Hermes on iOS (#53579)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53579

Changelog: [IOS][ADDED] Added opt-in to use the new Hermes

Reviewed By: cipolleschi

Differential Revision: D81035113

fbshipit-source-id: b12ca68824ec4e736edd4393a93c28803312eb32
2025-09-08 14:34:56 +01:00
Jakub PiaseckiandVitali Zaidman dc585b0f05 Gate legacy debugger behind a preprocessor directive (#53578)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53578

Changelog: [Internal]

Adds a new preprocessor directive which should be set when the new Hermes is being used. This directive will disable the legacy debugger which isn't supported by it.

Reviewed By: cipolleschi, cortinico

Differential Revision: D81035112

fbshipit-source-id: b30ae348b3419ec2d064dfe7f91c9d664a66f5cf
2025-09-08 14:34:46 +01:00
Phil PluckthunandVitali Zaidman 26cc647db3 Replace execSync with spawnSync for tarball extraction paths that need to be escaped (#53540)
Summary:
Follow-up to https://github.com/facebook/react-native/issues/53194

This wasn't previously visible in testing without prebuilds and without a release build. This doesn't show up in debug builds.

When testing more against paths that contain spaces, I noticed that release builds can still run into trouble due to the use of `execSync` without escaping paths. While, in other scripts that aren't used in user-projects (afaict), we often escape with quotes and rely on `execSync` calling the shell (due to its `shell: true` default), in some scripts we don't have quote escapes.

That said, since paths could in theory contain quotes, adding quotes wouldn't be sufficient. Instead, since the affected `tar` calls are really trivial, we can instead use `spawnSync` with the `shell: false` default, which escapes arguments automatically.

## Changelog:

[IOS] [FIXED] - fix Node scripts related to prebuilt tarball extraction for paths containing whitespaces

Pull Request resolved: https://github.com/facebook/react-native/pull/53540

Test Plan: - Create a project in a folder `with spaces` and build a release build

Reviewed By: cipolleschi, cortinico

Differential Revision: D81406841

Pulled By: robhogan

fbshipit-source-id: 08bb06b2cd2b15dc17c2f95fab9024129deca6f3
2025-09-08 14:33:39 +01:00
Riccardo CipolleschiandVitali Zaidman f194ee5626 Fix build with Cocopaods and Dynamic frameworks (#53367)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53367

We are missing a dependency in the React-jsinspector podspec that prevents React Native from building with dynamic frameworks.

## Changelog:
[Internal] -

Reviewed By: cortinico

Differential Revision: D80619664

fbshipit-source-id: 1c87ef4d3614ceea3a23196831479ecae0a5acc8
2025-09-08 14:33:19 +01:00
Phil PluckthunandVitali Zaidman b6c338780c Use autolinking react-native-config output in iOS artifacts generator (#53503)
Summary:
Resolves https://github.com/facebook/react-native/issues/53501

This is a pretty major oversight of (presumably) the old autolinking refactor. The iOS autolinking's second stage, invoked in `use_react_native!` does not accept the `react-native-config` sub-command's `react-native-config` output. This is only invoked and used in the prior step, `use_native_modules`.

The second step instead invokes old code that does something _similar_ to the new autolinking in `scripts/generate-artifacts-executor`, and happens to align in most cases. (But it does "autolinking" from scratch). tl;dr: When the results don't match up, things go wrong.

Instead, we now write the autolinking (react native config) results to a file, then read the output back in the second step.

This doesn't affect Android/Gradle, which are implemented correctly.

## Changelog:

[IOS] [FIXED] - Use autolinking-generated react-native-config output in second step of cocoapods linking that generates artifacts and generated source

Pull Request resolved: https://github.com/facebook/react-native/pull/53503

Test Plan:
- See https://github.com/facebook/react-native/issues/53501 for failing repro
- Clone for working repro: https://github.com/byCedric/react-native-codegen-ios-autolinking/tree/fix-54503
  - Note: Contains this PR's changes as a patch
  - `bun install`
  - `bun expo run:ios`

Reviewed By: cortinico

Differential Revision: D81490755

Pulled By: cipolleschi

fbshipit-source-id: eefe786a116404f4ed24bd7125dfb108a811f71e
2025-09-08 14:32:59 +01:00
Nicola CortiandVitali Zaidman f49ae8a388 Fix build from source for 0.82 due to Gradle 9.0 (#53560)
Summary:
Pull Request resolved: https://github.com/facebook/react-native/pull/53560

Since Gradle 9.0, all the projects in the path must have an existing folder.
As we build :packages:react-native:ReactAndroid, we need to declare the folders
for :packages and :packages:react-native as well as otherwise the build from
source will fail with a missing folder exception.

Changelog:
[Android] [Fixed] - Fix build from source due to missing folder error on Gradle 9.0

Reviewed By: fabriziocucci

Differential Revision: D81482789

fbshipit-source-id: 609b503755486e10060a0f321bd0a38bd71864a1
2025-09-08 14:32:28 +01:00
Moti ZilbermanandGitHub fdc4da96e4 Distribute React Native DevTools binaries via GitHub Releases (#52930) (#53604)
Summary:
bypass-github-export-checks

OSS release infrastructure for the (experimental) React Native DevTools standalone shell.

Currently, binaries are built continuously on Meta infra and served from the Meta CDN using fbcdn.net URLs checked into a DotSlash file in the repo, e.g.:

https://github.com/facebook/react-native/blob/15373218ec572c0e43325845b80a849ad5174cc3/packages/debugger-shell/bin/react-native-devtools#L9-L18

For open source releases we want to primarily distribute the binaries as GitHub release assets, while keeping the Meta CDN URLs as a secondary option. This PR makes the necessary changes to the release workflows to support this:

* `workflows/create-release.yml` (modified): As part of the release commit, rewrite the DotSlash file to include the release asset URLs.
  * **NOTE:** After this commit, **the new URLs don't work yet**, because they refer to a release that hasn't been published. Despite this, the DotSlash file remains valid and usable (because DotSlash will happily fall back to the Meta CDN URLs, which are still in the file).
* `workflows/create-draft-release.yml` (modified): After creating a draft release, fetch the binaries from the Meta CDN and reupload them to GitHub as release assets. This is based on the contents of the DotSlash file rewritten by `create-release.yml`.
* `workflows/validate-dotslash-artifacts.yml` (new): After the release is published, all URLs referenced by the DotSlash (both Meta CDN URL and GH release asset URLs) should be valid and refer to the same artifacts. This workflow checks that this is the case.
  * If this workflow fails on a published release, the release may need to be burned or a hotfix release may be necessary - as the release will stop working correctly once the Meta CDN stops serving the assets.
  * This workflow will also be running continuously on `main`. If it fails on a commit in `main`, there might be a connectivity issue between the GHA runner and the Meta CDN, or there might be an issue on the Meta side.

NOTE: These changes to the release pipeline are generic and reusable; if we later add another DotSlash-based tool whose binaries need to be mirrored as GitHub release assets, we just need to add it to the `FIRST_PARTY_DOTSLASH_FILES` array.

[Internal] Mirror React Native DevTools binaries in GitHub Releases

Pull Request resolved: https://github.com/facebook/react-native/pull/52930

Test Plan:

I've added unit tests for `dotslash-utils`, `curl-utils`, and for the majority of the logic that makes up the new release scripts (`write-dotslash-release-assets-urls`, `upload-release-assets-for-dotslash`, `validate-dotslash-artifacts`).

Created a test branch and draft PR: https://github.com/facebook/react-native/pull/53147.

Locally created a release commit, simulating the create-release GH workflow:

```
node scripts/releases/create-release-commit.js --reactNativeVersion 0.82.0-20250903-0830 --no-dry-run
```

This updated the DotSlash file in the branch: https://github.com/facebook/react-native/pull/53147/commits/2deeb7e70376ee80b99f27bea4825789f22a89a3#diff-205a9ff6005e30be061eaa64b9cb50b15b0e909dd188e0866189e952655a3483

NOTE: I've also ensured that the `create-release-commit` script correctly updates the DotSlash file when running from a branch that already has a release commit - see screenshot:
<img width="1483" height="587" alt="image" src="https://github.com/user-attachments/assets/1ffd859b-e02b-483d-8067-9cc9116829a4" />

Enabled testing the create-draft-release GH workflow in the test branch using these temporary hacks:

* https://github.com/facebook/react-native/pull/53147/commits/81f334eac5147d4dbf5f6d7d627ddfa52cd197be
* https://github.com/facebook/react-native/pull/53147/commits/6d8851657629de7e0b710ed8f5dd7d0f7b9847cc
* https://github.com/facebook/react-native/pull/53147/commits/1428a8da8b9fb29c45fc33d79f311dd1fe273433

Workflow run: https://github.com/facebook/react-native/actions/runs/17426711373/job/49475327346
Draft release: https://github.com/facebook/react-native/releases/tag/untagged-c6a62a58e5baa37936e1
Draft release screenshot for posterity (since we'll likely delete the draft release after landing this):

<img width="1024" height="814" alt="image" src="https://github.com/user-attachments/assets/1900da15-48f6-4274-b29c-0ac2019d92c0" />

For obvious reasons, I've avoided actually publishing the above draft release. But I have run the `validate-dotslash-artifacts` workflow on the *current* branch to ensure that the logic is correct: https://github.com/motiz88/react-native/actions/runs/17426885205/job/49475888486

Running `node scripts/releases/validate-dotslash-artifacts.js` in the release branch (without publishing the release first) fails, as expected:

<img width="1105" height="748" alt="image" src="https://github.com/user-attachments/assets/ed23a2e2-7a31-42eb-a324-f1d50eafe2fb" />

This PR is all the infra needed ahead of the 0.82 ~~branch cut~~ infra freeze to support the React Native DevTools standalone shell, at least on the GitHub side. ~~Some minor infra work remains on the Meta side, plus some product/logic changes to the React Native DevTools standalone shell that I'm intending to finish in time for 0.82 (for an experimental rollout).~~ EDIT: All the planned work has landed; the feature is code-complete on `main` as well as in `0.82-stable` (apart from this infra change).

As a one-off, once we've actually published 0.82.0-rc.1, we'll want to have a human look at the published artifacts and CI workflow logs to ensure everything is in order. (I'll make sure to communicate this to the 0.82 release crew.) Afterwards, the automation added in this PR should be sufficient.

Reviewed By: huntie

Differential Revision: D81578704

Pulled By: motiz88

fbshipit-source-id: 6a4a48c3713221a89dd5fc88851674c1ddc6bb10
2025-09-08 14:19:54 +01:00
Vitali Zaidman e5647a18a8 Update Podfile.lock
Changelog: [Internal]
2025-09-02 13:08:14 +01:00
React Native Bot 044d07c670 Release 0.82.0-rc.0
#publish-packages-to-npm&next
2025-09-02 10:05:17 +00:00
Vitali Zaidman 1b359eefba fixed artifacts not found in release-testing script 2025-09-01 18:28:54 +01:00
Vitali Zaidman 92b33c986c Bump hermes version 2025-09-01 16:43:10 +01:00
1750 changed files with 47733 additions and 67385 deletions
-3
View File
@@ -35,9 +35,6 @@ module.exports = {
// Flow handles these checks for us, so they aren't required
'no-undef': 'off',
'no-unreachable': 'off',
// Throwing from function or rejecting promises with non-error values could result in unclear error stack traces and lead to harder debugging
'prefer-promise-reject-errors': 'error',
'no-throw-literal': 'error',
},
},
{
+7 -2
View File
@@ -69,12 +69,17 @@ munge_underscores=true
module.name_mapper='^react-native$' -> '<PROJECT_ROOT>/packages/react-native/index.js'
module.name_mapper='^react-native/\(.*\)$' -> '<PROJECT_ROOT>/packages/react-native/\1'
module.name_mapper='^@react-native/dev-middleware$' -> '<PROJECT_ROOT>/packages/dev-middleware'
module.name_mapper='^@?[./a-zA-Z0-9$_-]+\.\(bmp\|gif\|jpg\|jpeg\|png\|psd\|svg\|webp\|m4v\|mov\|mp4\|mpeg\|mpg\|webm\|aac\|aiff\|caf\|m4a\|mp3\|wav\|html\|pdf\|xml\|ktx\)$' -> '<PROJECT_ROOT>/packages/react-native/Libraries/Image/RelativeImageStub'
module.name_mapper='^@?[./a-zA-Z0-9$_-]+\.\(bmp\|gif\|jpg\|jpeg\|png\|psd\|svg\|webp\|m4v\|mov\|mp4\|mpeg\|mpg\|webm\|aac\|aiff\|caf\|m4a\|mp3\|wav\|html\|pdf\|xml\)$' -> '<PROJECT_ROOT>/packages/react-native/Libraries/Image/RelativeImageStub'
module.system.haste.module_ref_prefix=m#
react.runtime=automatic
experimental.only_support_flow_fixme_and_expected_error=true
experimental.require_suppression_with_error_code=true
experimental.invariant_subtyping_error_message_improvement=true
experimental.natural_inference.local_object_literals.followup_fix=true
ban_spread_key_props=true
[lints]
@@ -98,4 +103,4 @@ untyped-import
untyped-type-import
[version]
^0.289.0
^0.280.0
-3
View File
@@ -17,9 +17,6 @@ runs:
- name: Install node dependencies
uses: ./.github/actions/yarn-install
- name: Set React Native Version
# We don't want to set the version for stable branches, because this has been
# already set from the 'create release' commits on the release branch.
if: ${{ !endsWith(github.ref_name, '-stable') }}
shell: bash
run: node ./scripts/releases/set-rn-artifacts-version.js --build-type ${{ inputs.release-type }}
- name: Setup gradle
@@ -0,0 +1,103 @@
name: build-apple-slices-hermes
description: This action builds hermesc for Apple platforms
inputs:
hermes-version:
required: true
description: The version of Hermes
react-native-version:
required: true
description: The version of Hermes
slice:
required: true
description: The slice of hermes you want to build. It could be iphone, iphonesimulator, macos, catalyst, appletvos, appletvsimulator, xros, or xrossimulator
flavor:
required: true
description: The flavor we want to build. It can be Debug or Release
runs:
using: composite
steps:
- name: Setup xcode
uses: ./.github/actions/setup-xcode
- name: Restore Hermes workspace
uses: ./.github/actions/restore-hermes-workspace
- name: Restore HermesC Artifact
uses: actions/download-artifact@v4
with:
name: hermesc-apple
path: ./packages/react-native/sdks/hermes/build_host_hermesc
- name: Restore Slice From Cache
id: restore-slice-cache
uses: actions/cache/restore@v4
with:
path: ./packages/react-native/sdks/hermes/build_${{ inputs.slice }}_${{ inputs.flavor }}
key: v6-hermes-apple-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}-${{ hashfiles('packages/react-native/sdks/hermes-engine/utils/build-apple-framework.sh') }}-${{ inputs.slice }}-${{ inputs.flavor }}
- name: Build the Hermes ${{ inputs.slice }} frameworks
shell: bash
run: |
cd ./packages/react-native/sdks/hermes || exit 1
SLICE=${{ inputs.slice }}
FLAVOR=${{ inputs.flavor }}
FINAL_PATH=build_"$SLICE"_"$FLAVOR"
echo "Final path for this slice is: $FINAL_PATH"
if [[ -d "$FINAL_PATH" ]]; then
echo "[HERMES] Skipping! Found the requested slice at $FINAL_PATH".
exit 0
fi
if [[ "$ARTIFACTS_EXIST" ]]; then
echo "[HERMES] Skipping! Artifacts exists already."
exit 0
fi
export RELEASE_VERSION=${{ inputs.react-native-version }}
# HermesC is used to build hermes, so it has to be executable
chmod +x ./build_host_hermesc/bin/hermesc
if [[ "$SLICE" == "macosx" ]]; then
echo "[HERMES] Building Hermes for MacOS"
chmod +x ./utils/build-mac-framework.sh
BUILD_TYPE="${{ inputs.flavor }}" ./utils/build-mac-framework.sh
else
echo "[HERMES] Building Hermes for iOS: $SLICE"
chmod +x ./utils/build-ios-framework.sh
BUILD_TYPE="${{ inputs.flavor }}" ./utils/build-ios-framework.sh "$SLICE"
fi
echo "Moving from build_$SLICE to $FINAL_PATH"
mv build_"$SLICE" "$FINAL_PATH"
# check whether everything is there
if [[ -d "$FINAL_PATH/lib/hermesvm.framework" ]]; then
echo "Successfully built hermesvm.framework for $SLICE in $FLAVOR"
else
echo "Failed to built hermesvm.framework for $SLICE in $FLAVOR"
exit 1
fi
if [[ -d "$FINAL_PATH/lib/hermesvm.framework.dSYM" ]]; then
echo "Successfully built hermesvm.framework.dSYM for $SLICE in $FLAVOR"
else
echo "Failed to built hermesvm.framework.dSYM for $SLICE in $FLAVOR"
echo "Please try again"
exit 1
fi
- name: Compress slices to preserve Symlinks
shell: bash
run: |
cd ./packages/react-native/sdks/hermes
tar -czv -f build_${{ matrix.slice }}_${{ matrix.flavor }}.tar.gz build_${{ matrix.slice }}_${{ matrix.flavor }}
- name: Upload Artifact for Slice (${{ inputs.slice }}, ${{ inputs.flavor }}}
uses: actions/upload-artifact@v4.3.4
with:
name: slice-${{ inputs.slice }}-${{ inputs.flavor }}
path: ./packages/react-native/sdks/hermes/build_${{ inputs.slice }}_${{ inputs.flavor }}.tar.gz
- name: Save slice cache
if: ${{ github.ref == 'refs/heads/main' || contains(github.ref, '-stable') }} # To avoid that the cache explode.
uses: actions/cache/save@v4
with:
path: ./packages/react-native/sdks/hermes/build_${{ inputs.slice }}_${{ inputs.flavor }}
key: v6-hermes-apple-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}-${{ hashfiles('packages/react-native/sdks/hermes-engine/utils/build-apple-framework.sh') }}-${{ inputs.SLICE }}-${{ inputs.FLAVOR }}
@@ -0,0 +1,227 @@
name: build-hermes-macos
description: This action builds hermesc for Apple platforms
inputs:
hermes-version:
required: true
description: The version of Hermes
react-native-version:
required: true
description: The version of React Native
flavor:
required: true
description: The flavor we want to build. It can be Debug or Release
runs:
using: composite
steps:
- name: Setup xcode
uses: ./.github/actions/setup-xcode
- name: Restore Hermes workspace
uses: ./.github/actions/restore-hermes-workspace
- name: Restore Cached Artifacts
uses: actions/cache/restore@v4
with:
key: v4-hermes-artifacts-${{ inputs.flavor }}-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}-${{ hashFiles('./packages/react-native/sdks/hermes-engine/utils/build-apple-framework.sh') }}
path: |
/tmp/hermes/osx-bin/${{ inputs.flavor }}
/tmp/hermes/dSYM/${{ inputs.flavor }}
/tmp/hermes/hermes-runtime-darwin/hermes-ios-${{ inputs.flavor }}.tar.gz
- name: Check if the required artifacts already exist
id: check_if_apple_artifacts_are_there
shell: bash
run: |
FLAVOR="${{ inputs.flavor }}"
echo "Flavor is $FLAVOR"
OSX_BIN="/tmp/hermes/osx-bin/$FLAVOR"
DSYM="/tmp/hermes/dSYM/$FLAVOR"
HERMES="/tmp/hermes/hermes-runtime-darwin/hermes-ios-$FLAVOR.tar.gz"
if [[ -d "$OSX_BIN" ]] && \
[[ -d "$DSYM" ]] && \
[[ -f "$HERMES" ]]; then
echo "Artifacts are there!"
echo "ARTIFACTS_EXIST=true" >> $GITHUB_ENV
echo "ARTIFACTS_EXIST=true" >> $GITHUB_OUTPUT
fi
- name: Setup node.js
uses: ./.github/actions/setup-node
- name: Yarn- Install Dependencies
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: ./.github/actions/yarn-install
- name: Slice cache macosx
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-macosx-${{ inputs.flavor }}
- name: Slice cache iphoneos
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-iphoneos-${{ inputs.flavor }}
- name: Slice cache iphonesimulator
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-iphonesimulator-${{ inputs.flavor }}
- name: Slice cache appletvos
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-appletvos-${{ inputs.flavor }}
- name: Slice cache appletvsimulator
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-appletvsimulator-${{ inputs.flavor }}
- name: Slice cache catalyst
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-catalyst-${{ inputs.flavor }}
- name: Slice cache xros
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-xros-${{ inputs.flavor }}
- name: Slice cache xrsimulator
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
uses: actions/download-artifact@v4
with:
path: ./packages/react-native/sdks/hermes/
name: slice-xrsimulator-${{ inputs.flavor }}
- name: Unzip slices
shell: bash
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
run: |
cd ./packages/react-native/sdks/hermes
ls -l .
tar -xzv -f build_catalyst_${{ matrix.flavor }}.tar.gz
tar -xzv -f build_iphoneos_${{ matrix.flavor }}.tar.gz
tar -xzv -f build_iphonesimulator_${{ matrix.flavor }}.tar.gz
tar -xzv -f build_appletvos_${{ matrix.flavor }}.tar.gz
tar -xzv -f build_appletvsimulator_${{ matrix.flavor }}.tar.gz
tar -xzv -f build_macosx_${{ matrix.flavor }}.tar.gz
tar -xzv -f build_xros_${{ matrix.flavor }}.tar.gz
tar -xzv -f build_xrsimulator_${{ matrix.flavor }}.tar.gz
- name: Move back build folders
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
shell: bash
run: |
ls -l ./packages/react-native/sdks/hermes
cd ./packages/react-native/sdks/hermes || exit 1
mv build_macosx_${{ inputs.flavor }} build_macosx
mv build_iphoneos_${{ inputs.flavor }} build_iphoneos
mv build_iphonesimulator_${{ inputs.flavor }} build_iphonesimulator
mv build_appletvos_${{ inputs.flavor }} build_appletvos
mv build_appletvsimulator_${{ inputs.flavor }} build_appletvsimulator
mv build_catalyst_${{ inputs.flavor }} build_catalyst
mv build_xros_${{ inputs.flavor }} build_xros
mv build_xrsimulator_${{ inputs.flavor }} build_xrsimulator
- name: Prepare destroot folder
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
shell: bash
run: |
cd ./packages/react-native/sdks/hermes || exit 1
chmod +x ./utils/build-apple-framework.sh
. ./utils/build-apple-framework.sh
prepare_dest_root_for_ci
- name: Create fat framework for iOS
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
shell: bash
run: |
cd ./packages/react-native/sdks/hermes || exit 1
echo "[HERMES] Creating the universal framework"
chmod +x ./utils/build-ios-framework.sh
./utils/build-ios-framework.sh build_framework
chmod +x ./destroot/bin/hermesc
- name: Package the Hermes Apple frameworks
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
shell: bash
run: |
BUILD_TYPE="${{ inputs.flavor }}"
echo "Packaging Hermes Apple frameworks for $BUILD_TYPE build type"
TARBALL_OUTPUT_DIR=$(mktemp -d /tmp/hermes-tarball-output-XXXXXXXX)
TARBALL_FILENAME=$(node ./packages/react-native/scripts/hermes/get-tarball-name.js --buildType "$BUILD_TYPE")
echo "Packaging Hermes Apple frameworks for $BUILD_TYPE build type"
TARBALL_OUTPUT_PATH=$(node ./packages/react-native/scripts/hermes/create-tarball.js \
--inputDir ./packages/react-native/sdks/hermes \
--buildType "$BUILD_TYPE" \
--outputDir $TARBALL_OUTPUT_DIR)
echo "Hermes tarball saved to $TARBALL_OUTPUT_PATH"
mkdir -p $HERMES_TARBALL_ARTIFACTS_DIR
cp $TARBALL_OUTPUT_PATH $HERMES_TARBALL_ARTIFACTS_DIR/.
mkdir -p /tmp/hermes/osx-bin/${{ inputs.flavor }}
cp ./packages/react-native/sdks/hermes/build_macosx/bin/* /tmp/hermes/osx-bin/${{ inputs.flavor }}
ls -lR /tmp/hermes/osx-bin/
- name: Create dSYM archive
if: ${{ steps.check_if_apple_artifacts_are_there.outputs.ARTIFACTS_EXIST != 'true' }}
shell: bash
run: |
FLAVOR=${{ inputs.flavor }}
WORKING_DIR="/tmp/hermes_tmp/dSYM/$FLAVOR"
mkdir -p "$WORKING_DIR/macosx"
mkdir -p "$WORKING_DIR/catalyst"
mkdir -p "$WORKING_DIR/iphoneos"
mkdir -p "$WORKING_DIR/iphonesimulator"
mkdir -p "$WORKING_DIR/appletvos"
mkdir -p "$WORKING_DIR/appletvsimulator"
mkdir -p "$WORKING_DIR/xros"
mkdir -p "$WORKING_DIR/xrsimulator"
cd ./packages/react-native/sdks/hermes || exit 1
DSYM_FILE_PATH=lib/hermesvm.framework.dSYM
cp -r build_macosx/$DSYM_FILE_PATH "$WORKING_DIR/macosx/"
cp -r build_catalyst/$DSYM_FILE_PATH "$WORKING_DIR/catalyst/"
cp -r build_iphoneos/$DSYM_FILE_PATH "$WORKING_DIR/iphoneos/"
cp -r build_iphonesimulator/$DSYM_FILE_PATH "$WORKING_DIR/iphonesimulator/"
cp -r build_appletvos/$DSYM_FILE_PATH "$WORKING_DIR/appletvos/"
cp -r build_appletvsimulator/$DSYM_FILE_PATH "$WORKING_DIR/appletvsimulator/"
cp -r build_xros/$DSYM_FILE_PATH "$WORKING_DIR/xros/"
cp -r build_xrsimulator/$DSYM_FILE_PATH "$WORKING_DIR/xrsimulator/"
DEST_DIR="/tmp/hermes/dSYM/$FLAVOR"
tar -C "$WORKING_DIR" -czvf "hermesvm.framework.dSYM" .
mkdir -p "$DEST_DIR"
mv "hermesvm.framework.dSYM" "$DEST_DIR"
- name: Upload hermes dSYM artifacts
uses: actions/upload-artifact@v4.3.4
with:
name: hermes-dSYM-${{ inputs.flavor }}
path: /tmp/hermes/dSYM/${{ inputs.flavor }}
- name: Upload hermes Runtime artifacts
uses: actions/upload-artifact@v4.3.4
with:
name: hermes-darwin-bin-${{ inputs.flavor }}
path: /tmp/hermes/hermes-runtime-darwin/hermes-ios-${{ inputs.flavor }}.tar.gz
- name: Upload hermes osx artifacts
uses: actions/upload-artifact@v4.3.4
with:
name: hermes-osx-bin-${{ inputs.flavor }}
path: /tmp/hermes/osx-bin/${{ inputs.flavor }}
- name: Upload Hermes Artifacts
uses: actions/cache/save@v4
if: ${{ github.ref == 'refs/heads/main' || contains(github.ref, '-stable') }} # To avoid that the cache explode.
with:
key: v4-hermes-artifacts-${{ inputs.flavor }}-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}-${{ hashFiles('./packages/react-native/sdks/hermes-engine/utils/build-apple-framework.sh') }}
path: |
/tmp/hermes/osx-bin/${{ inputs.flavor }}
/tmp/hermes/dSYM/${{ inputs.flavor }}
/tmp/hermes/hermes-runtime-darwin/hermes-ios-${{ inputs.flavor }}.tar.gz
@@ -0,0 +1,39 @@
name: build-hermesc-apple
description: This action builds hermesc for Apple platforms
inputs:
hermes-version:
required: true
description: The version of Hermes
react-native-version:
required: true
description: The version of React Native
runs:
using: composite
steps:
- name: Setup xcode
uses: ./.github/actions/setup-xcode
- name: Restore Hermes workspace
uses: ./.github/actions/restore-hermes-workspace
- name: Hermes apple cache
uses: actions/cache/restore@v4
with:
path: ./packages/react-native/sdks/hermes/build_host_hermesc
key: v2-hermesc-apple-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}
- name: Build HermesC Apple
shell: bash
run: |
cd ./packages/react-native/sdks/hermes || exit 1
. ./utils/build-apple-framework.sh
build_host_hermesc_if_needed
- name: Upload HermesC Artifact
uses: actions/upload-artifact@v4.3.4
with:
name: hermesc-apple
path: ./packages/react-native/sdks/hermes/build_host_hermesc
- name: Cache hermesc apple
uses: actions/cache/save@v4
if: ${{ github.ref == 'refs/heads/main' || contains(github.ref, '-stable') }} # To avoid that the cache explode.
with:
path: ./packages/react-native/sdks/hermes/build_host_hermesc
key: v2-hermesc-apple-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}
enableCrossOsArchive: true
@@ -0,0 +1,53 @@
name: build-hermesc-linux
description: This action builds hermesc for linux platforms
inputs:
hermes-version:
required: True
description: The version of Hermes
react-native-version:
required: True
description: The version of React Native
runs:
using: composite
steps:
- name: Install dependencies
shell: bash
run: |
sudo apt update
sudo apt install -y git openssh-client build-essential \
libreadline-dev libicu-dev jq zip python3
# Install cmake 3.28.3-1build7
sudo apt-get install cmake=3.28.3-1build7
sudo ln -sf /usr/bin/cmake /usr/local/bin/cmake
- name: Restore Hermes workspace
uses: ./.github/actions/restore-hermes-workspace
- name: Linux cache
uses: actions/cache@v4
with:
key: v1-hermes-${{ github.job }}-linux-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}
path: |
/tmp/hermes/linux64-bin/
/tmp/hermes/hermes/destroot/
- name: Set up workspace
shell: bash
run: |
mkdir -p /tmp/hermes/linux64-bin
- name: Build HermesC for Linux
shell: bash
run: |
if [ -f /tmp/hermes/linux64-bin/hermesc ]; then
echo 'Skipping; Clean "/tmp/hermes/linux64-bin" to rebuild.'
else
cd /tmp/hermes
cmake -S hermes -B build -DHERMES_STATIC_LINK=ON -DCMAKE_BUILD_TYPE=Release -DHERMES_ENABLE_TEST_SUITE=OFF \
-DCMAKE_INTERPROCEDURAL_OPTIMIZATION=True -DCMAKE_CXX_FLAGS=-s -DCMAKE_C_FLAGS=-s \
-DCMAKE_EXE_LINKER_FLAGS="-Wl,--whole-archive -lpthread -Wl,--no-whole-archive"
cmake --build build --target hermesc -j 4
cp /tmp/hermes/build/bin/hermesc /tmp/hermes/linux64-bin/.
fi
- name: Upload linux artifacts
uses: actions/upload-artifact@v4.3.4
with:
name: hermes-linux-bin
path: /tmp/hermes/linux64-bin
@@ -0,0 +1,86 @@
name: build-hermesc-windows
description: This action builds hermesc for Windows platforms
inputs:
hermes-version:
required: True
description: The version of Hermes
react-native-version:
required: True
description: The version of React Native
runs:
using: composite
steps:
- name: Download Previous Artifacts
uses: actions/download-artifact@v4
with:
name: hermes-workspace
path: 'C:\tmp\hermes'
- name: Set up workspace
shell: powershell
run: |
mkdir -p C:\tmp\hermes\osx-bin
mkdir -p .\packages\react-native\sdks\hermes
cp -r -Force C:\tmp\hermes\hermes\* .\packages\react-native\sdks\hermes\.
cp -r -Force .\packages\react-native\sdks\hermes-engine\utils\* .\packages\react-native\sdks\hermes\.
- name: Windows cache
uses: actions/cache@v4
with:
key: v3-hermes-${{ github.job }}-windows-${{ inputs.hermes-version }}-${{ inputs.react-native-version }}
path: |
C:\tmp\hermes\win64-bin\
C:\tmp\hermes\hermes\icu\
C:\tmp\hermes\hermes\deps\
C:\tmp\hermes\hermes\build_release\
- name: setup-msbuild
uses: microsoft/setup-msbuild@v1.3.2
- name: Set up workspace
shell: powershell
run: |
New-Item -ItemType Directory -ErrorAction SilentlyContinue $Env:HERMES_WS_DIR\icu
New-Item -ItemType Directory -ErrorAction SilentlyContinue $Env:HERMES_WS_DIR\deps
New-Item -ItemType Directory -ErrorAction SilentlyContinue $Env:HERMES_WS_DIR\win64-bin
- name: Downgrade CMake
shell: powershell
run: choco install cmake --version 3.31.6 --force
- name: Build HermesC for Windows
shell: powershell
run: |
if (-not(Test-Path -Path $Env:HERMES_WS_DIR\win64-bin\hermesc.exe)) {
cd $Env:HERMES_WS_DIR\icu
# If Invoke-WebRequest shows a progress bar, it will fail with
# Win32 internal error "Access is denied" 0x5 occurred [...]
$progressPreference = 'silentlyContinue'
Invoke-WebRequest -Uri "$Env:ICU_URL" -OutFile "icu.zip"
Expand-Archive -Path "icu.zip" -DestinationPath "."
cd $Env:HERMES_WS_DIR
Copy-Item -Path "icu\bin64\icu*.dll" -Destination "deps"
# Include MSVC++ 2015 redistributables
Copy-Item -Path "c:\windows\system32\msvcp140.dll" -Destination "deps"
Copy-Item -Path "c:\windows\system32\vcruntime140.dll" -Destination "deps"
Copy-Item -Path "c:\windows\system32\vcruntime140_1.dll" -Destination "deps"
$Env:PATH += ";$Env:CMAKE_DIR;$Env:MSBUILD_DIR"
$Env:ICU_ROOT = "$Env:HERMES_WS_DIR\icu"
cmake -S hermes -B build_release -G 'Visual Studio 17 2022' -Ax64 -DCMAKE_BUILD_TYPE=Release -DCMAKE_INTERPROCEDURAL_OPTIMIZATION=True -DHERMES_ENABLE_WIN10_ICU_FALLBACK=OFF
if (-not $?) { throw "Failed to configure Hermes" }
echo "Running windows build..."
cd build_release
cmake --build . --target hermesc --config Release
if (-not $?) { throw "Failed to build Hermes" }
echo "Copying hermesc.exe to win64-bin"
cd $Env:HERMES_WS_DIR
Copy-Item -Path "build_release\bin\Release\hermesc.exe" -Destination "win64-bin"
# Include Windows runtime dependencies
Copy-Item -Path "deps\*" -Destination "win64-bin"
}
else {
Write-Host "Skipping; Clean c:\tmp\hermes\win64-bin to rebuild."
}
- name: Upload windows artifacts
uses: actions/upload-artifact@v4.3.4
with:
name: hermes-win64-bin
path: C:\tmp\hermes\win64-bin\
@@ -4,6 +4,9 @@ inputs:
release-type:
required: true
description: The type of release we are building. It could be nightly, release or dry-run
hermes-ws-dir:
required: 'true'
description: The workspace for hermes
gha-npm-token:
required: false
description: The GHA npm token, required only to publish to npm
@@ -17,6 +20,87 @@ runs:
- name: Setup git safe folders
shell: bash
run: git config --global --add safe.directory '*'
- name: Create /tmp/hermes/osx-bin directory
shell: bash
run: mkdir -p /tmp/hermes/osx-bin
- name: Download osx-bin release artifacts
uses: actions/download-artifact@v4
with:
name: hermes-osx-bin-Release
path: /tmp/hermes/osx-bin/Release
- name: Download osx-bin debug artifacts
uses: actions/download-artifact@v4
with:
name: hermes-osx-bin-Debug
path: /tmp/hermes/osx-bin/Debug
- name: Download darwin-bin release artifacts
uses: actions/download-artifact@v4
with:
name: hermes-darwin-bin-Release
path: /tmp/hermes/hermes-runtime-darwin
- name: Download darwin-bin debug artifacts
uses: actions/download-artifact@v4
with:
name: hermes-darwin-bin-Debug
path: /tmp/hermes/hermes-runtime-darwin
- name: Download hermes dSYM debug artifacts
uses: actions/download-artifact@v4
with:
name: hermes-dSYM-Debug
path: /tmp/hermes/dSYM/Debug
- name: Download hermes dSYM release vartifacts
uses: actions/download-artifact@v4
with:
name: hermes-dSYM-Release
path: /tmp/hermes/dSYM/Release
- name: Download windows-bin artifacts
uses: actions/download-artifact@v4
with:
name: hermes-win64-bin
path: /tmp/hermes/win64-bin
- name: Download linux-bin artifacts
uses: actions/download-artifact@v4
with:
name: hermes-linux-bin
path: /tmp/hermes/linux64-bin
- name: Show /tmp/hermes directory
shell: bash
run: ls -lR /tmp/hermes
- name: Copy Hermes binaries
shell: bash
run: |
mkdir -p ./packages/react-native/sdks/hermesc ./packages/react-native/sdks/hermesc/osx-bin ./packages/react-native/sdks/hermesc/win64-bin ./packages/react-native/sdks/hermesc/linux64-bin
# When build_hermes_macos runs as a matrix, it outputs
if [[ -d ${{ inputs.hermes-ws-dir }}/osx-bin/Release ]]; then
cp -r ${{ inputs.hermes-ws-dir }}/osx-bin/Release/* ./packages/react-native/sdks/hermesc/osx-bin/.
elif [[ -d ${{ inputs.hermes-ws-dir }}/osx-bin/Debug ]]; then
cp -r ${{ inputs.hermes-ws-dir }}/osx-bin/Debug/* ./packages/react-native/sdks/hermesc/osx-bin/.
else
ls ${{ inputs.hermes-ws-dir }}/osx-bin || echo "hermesc macOS artifacts directory missing."
echo "Could not locate macOS hermesc binary."; exit 1;
fi
# Sometimes, GHA creates artifacts with lowercase Debug/Release. Make sure that if it happen, we uppercase them.
if [[ -f "${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-debug.tar.gz" ]]; then
mv "${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-debug.tar.gz" "${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-Debug.tar.gz"
fi
if [[ -f "${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-release.tar.gz" ]]; then
mv "${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-release.tar.gz" "${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-Release.tar.gz"
fi
cp -r ${{ inputs.hermes-ws-dir }}/win64-bin/* ./packages/react-native/sdks/hermesc/win64-bin/.
cp -r ${{ inputs.hermes-ws-dir }}/linux64-bin/* ./packages/react-native/sdks/hermesc/linux64-bin/.
# Make sure the hermesc files are actually executable.
chmod -R +x packages/react-native/sdks/hermesc/*
mkdir -p ./packages/react-native/ReactAndroid/external-artifacts/artifacts/
cp ${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-Debug.tar.gz ./packages/react-native/ReactAndroid/external-artifacts/artifacts/hermes-ios-debug.tar.gz
cp ${{ inputs.hermes-ws-dir }}/hermes-runtime-darwin/hermes-ios-Release.tar.gz ./packages/react-native/ReactAndroid/external-artifacts/artifacts/hermes-ios-release.tar.gz
cp ${{ inputs.hermes-ws-dir }}/dSYM/Debug/hermesvm.framework.dSYM ./packages/react-native/ReactAndroid/external-artifacts/artifacts/hermes-framework-dSYM-debug.tar.gz
cp ${{ inputs.hermes-ws-dir }}/dSYM/Release/hermesvm.framework.dSYM ./packages/react-native/ReactAndroid/external-artifacts/artifacts/hermes-framework-dSYM-release.tar.gz
- name: Download ReactNativeDependencies
uses: actions/download-artifact@v4
with:
@@ -0,0 +1,99 @@
name: prepare-hermes-workspace
description: This action prepares the hermes workspace with the right hermes and react-native versions.
inputs:
hermes-ws-dir:
required: true
description: The hermes dir we need to use to setup the workspace
hermes-version-file:
required: true
description: the path to the file that will contain the hermes version
outputs:
hermes-version:
description: the version of Hermes tied to this run
value: ${{ steps.hermes-version.outputs.VERSION }}
react-native-version:
description: the version of React Native tied to this run
value: ${{ steps.react-native-version.outputs.VERSION }}
runs:
using: composite
steps:
- name: Setup hermes version
shell: bash
id: hermes-version
run: |
mkdir -p "/tmp/hermes" "/tmp/hermes/download" "/tmp/hermes/hermes"
if [ -f "${{ inputs.hermes-version-file }}" ]; then
echo "Hermes Version file found! Using this version for the build:"
echo "VERSION=$(cat ${{ inputs.hermes-version-file }})" >> "$GITHUB_OUTPUT"
else
echo "Hermes Version file not found!!!"
echo "Using the last commit from main for the build:"
HERMES_TAG_SHA=$(git ls-remote https://github.com/facebook/hermes main | cut -f 1 | tr -d '[:space:]')
echo "VERSION=$HERMES_TAG_SHA" >> "$GITHUB_OUTPUT"
fi
echo "Hermes commit is $HERMES_TAG_SHA"
- name: Get react-native version
shell: bash
id: react-native-version
run: |
VERSION=$(cat packages/react-native/package.json | jq -r '.version')
# Save the react native version we are building in an output variable so we can use that file as part of the cache key.
echo "VERSION=$VERSION" >> "$GITHUB_OUTPUT"
echo "React Native Version is $VERSION"
- name: Cache hermes workspace
id: restore-hermes
uses: actions/cache/restore@v4
with:
path: |
/tmp/hermes/download/
/tmp/hermes/hermes/
key: v1-hermes-${{ steps.hermes-version.outputs.version }}
enableCrossOsArchive: true
# It happened while testing that a cache was created from the right folders
# but those folders where empty. Thus, the next check ensures that we can work with those caches.
- name: Check if cache was meaningful
id: meaningful-cache
shell: bash
run: |
if [[ -d /tmp/hermes/hermes ]] && [[ -n "$(ls -A /tmp/hermes/hermes)" ]]; then
echo "Found a good hermes cache"
echo "HERMES_CACHED=true" >> "$GITHUB_OUTPUT"
fi
- name: Setup node.js
uses: ./.github/actions/setup-node
- name: Yarn- Install Dependencies
if: ${{ steps.meaningful-cache.outputs.HERMES_CACHED != 'true' }}
uses: ./.github/actions/yarn-install
- name: Download Hermes tarball
if: ${{ steps.meaningful-cache.outputs.HERMES_CACHED != 'true' }}
shell: bash
run: |
node packages/react-native/scripts/hermes/prepare-hermes-for-build ${{ github.event.pull_request.html_url }}
cp packages/react-native/sdks/download/* ${{ inputs.hermes-ws-dir }}/download/.
cp -r packages/react-native/sdks/hermes/* ${{ inputs.hermes-ws-dir }}/hermes/.
echo ${{ steps.hermes-version.outputs.version }}
- name: Upload Hermes artifact
uses: actions/upload-artifact@v4.3.4
with:
name: hermes-workspace
path: |
/tmp/hermes/download/
/tmp/hermes/hermes/
- name: Cache hermes workspace
uses: actions/cache/save@v4
if: ${{ github.ref == 'refs/heads/main' }} # To avoid that the cache explode.
with:
path: |
/tmp/hermes/download/
/tmp/hermes/hermes/
key: v1-hermes-${{ steps.hermes-version.outputs.version }}
enableCrossOsArchive: true
@@ -0,0 +1,16 @@
name: restore-hermes-workspace
description: "Restore hermes workspace that has been created in Prepare Hermes Workspace"
runs:
using: composite
steps:
- name: Download Previous Artifacts
uses: actions/download-artifact@v4
with:
name: hermes-workspace
path: /tmp/hermes
- name: Set up workspace
shell: bash
run: |
mkdir -p $HERMES_OSXBIN_ARTIFACTS_DIR ./packages/react-native/sdks/hermes
cp -r $HERMES_WS_DIR/hermes/* ./packages/react-native/sdks/hermes/.
cp -r ./packages/react-native/sdks/hermes-engine/utils ./packages/react-native/sdks/hermes/.
-22
View File
@@ -5,10 +5,6 @@ inputs:
description: 'The xcode version to use'
required: false
default: '16.2.0'
platform:
description: 'The platform to use. Valid values are: ios, ios-simulator, macos, mac-catalyst, tvos, tvos-simulator, xros, xros-simulator'
required: false
default: 'macos'
runs:
using: "composite"
steps:
@@ -16,21 +12,3 @@ runs:
uses: maxim-lobanov/setup-xcode@60606e260d2fc5762a71e64e74b2174e8ea3c8bd
with:
xcode-version: ${{ inputs.xcode-version }}
- name: Setup Platform ${{ inputs.platform }}
if: ${{ inputs.platform != 'macos' && inputs.platform != 'mac-catalyst' }}
shell: bash
run: |
# https://github.com/actions/runner-images/issues/12541
sudo xcodebuild -runFirstLaunch
sudo xcrun simctl list
# Install platform based on the platform
if [[ "${{ inputs.platform }}" == "xros" || "${{ inputs.platform }}" == "xros-simulator" ]]; then
sudo xcodebuild -downloadPlatform visionOS
elif [[ "${{ inputs.platform }}" == "tvos" || "${{ inputs.platform }}" == "tvos-simulator" ]]; then
sudo xcodebuild -downloadPlatform tvOS
else
sudo xcodebuild -downloadPlatform iOS
fi
sudo xcodebuild -runFirstLaunch
+31 -8
View File
@@ -10,27 +10,36 @@ inputs:
flavor:
description: The flavor of the build. Must be one of "Debug", "Release".
default: Debug
hermes-version:
description: The version of hermes
required: true
react-native-version:
description: The version of react-native
required: true
runs:
using: composite
steps:
- name: Setup xcode
uses: ./.github/actions/setup-xcode
with:
platform: ios
- name: Setup node.js
uses: ./.github/actions/setup-node
- name: Run yarn install
uses: ./.github/actions/yarn-install
- name: Create Hermes folder
shell: bash
run: mkdir -p "$HERMES_WS_DIR"
- name: Download Hermes
uses: actions/download-artifact@v4
with:
name: hermes-darwin-bin-${{ inputs.flavor }}
path: /tmp/hermes/hermes-runtime-darwin/
- name: Print Downloaded hermes
shell: bash
run: ls -lR "$HERMES_WS_DIR"
- name: Setup ruby
uses: ruby/setup-ruby@v1
with:
ruby-version: ${{ inputs.ruby-version }}
- name: Set nightly Hermes versions
shell: bash
run: |
node ./scripts/releases/use-hermes-nightly.js
- name: Run yarn install again, with the correct hermes version
uses: ./.github/actions/yarn-install
- name: Download ReactNativeDependencies
uses: actions/download-artifact@v4
with:
@@ -57,6 +66,20 @@ runs:
args+=(--frameworks dynamic)
fi
# Tarball is restored with capital flavors suffix, but somehow the tarball name from JS at line 96 returns as lowercased.
# Let's ensure that the tarballs have the right names
if [[ -f "$HERMES_WS_DIR/hermes-runtime-darwin/hermes-ios-Debug.tar.gz" ]]; then
mv "$HERMES_WS_DIR/hermes-runtime-darwin/hermes-ios-Debug.tar.gz" "$HERMES_WS_DIR/hermes-runtime-darwin/hermes-ios-debug.tar.gz"
fi
if [[ -f "$HERMES_WS_DIR/hermes-runtime-darwin/hermes-ios-Release.tar.gz" ]]; then
mv "$HERMES_WS_DIR/hermes-runtime-darwin/hermes-ios-Release.tar.gz" "$HERMES_WS_DIR/hermes-runtime-darwin/hermes-ios-release.tar.gz"
fi
BUILD_TYPE="${{ inputs.flavor }}"
TARBALL_FILENAME=$(node ../../packages/react-native/scripts/hermes/get-tarball-name.js --buildType "$BUILD_TYPE")
export HERMES_ENGINE_TARBALL_PATH="$HERMES_WS_DIR/hermes-runtime-darwin/$TARBALL_FILENAME"
export RCT_USE_LOCAL_RN_DEP="/tmp/third-party/ReactNativeDependencies${{ inputs.flavor }}.xcframework.tar.gz"
export RCT_TESTONLY_RNCORE_TARBALL_PATH="/tmp/ReactCore/ReactCore${{ inputs.flavor }}.xcframework.tar.gz"
+54 -9
View File
@@ -10,9 +10,18 @@ inputs:
run-unit-tests:
description: whether unit tests should run or not.
default: "false"
hermes-tarball-artifacts-dir:
description: The directory where the hermes tarball artifacts are stored
default: /tmp/hermes/hermes-runtime-darwin
flavor:
description: The flavor of the build. Must be one of "Debug", "Release".
default: Debug
hermes-version:
description: The version of hermes
required: true
react-native-version:
description: The version of react-native
required: true
run-e2e-tests:
description: Whether we want to run E2E tests or not
required: false
@@ -23,25 +32,60 @@ runs:
steps:
- name: Setup xcode
uses: ./.github/actions/setup-xcode
with:
platform: ios
- name: Setup node.js
uses: ./.github/actions/setup-node
- name: Run yarn
uses: ./.github/actions/yarn-install
- name: Download Hermes
uses: actions/download-artifact@v4
with:
name: hermes-darwin-bin-${{ inputs.flavor }}
path: ${{ inputs.hermes-tarball-artifacts-dir }}
- name: Setup ruby
uses: ruby/setup-ruby@v1
with:
ruby-version: ${{ inputs.ruby-version }}
- name: Set nightly Hermes versions
shell: bash
run: |
node ./scripts/releases/use-hermes-nightly.js
- name: Run yarn install again, with the correct hermes version
uses: ./.github/actions/yarn-install
- name: Prepare IOS Tests
if: ${{ inputs.run-unit-tests == 'true' }}
uses: ./.github/actions/prepare-ios-tests
- name: Set HERMES_ENGINE_TARBALL_PATH envvar if Hermes tarball is present
shell: bash
run: |
HERMES_TARBALL_ARTIFACTS_DIR=${{ inputs.hermes-tarball-artifacts-dir }}
if [ ! -d $HERMES_TARBALL_ARTIFACTS_DIR ]; then
echo "Hermes tarball artifacts dir not present ($HERMES_TARBALL_ARTIFACTS_DIR). Build Hermes from source."
exit 0
fi
TARBALL_FILENAME=$(node ./packages/react-native/scripts/hermes/get-tarball-name.js --buildType "${{ inputs.flavor }}")
TARBALL_PATH=$HERMES_TARBALL_ARTIFACTS_DIR/$TARBALL_FILENAME
echo "Looking for $TARBALL_FILENAME in $HERMES_TARBALL_ARTIFACTS_DIR"
echo "$TARBALL_PATH"
if [ ! -f $TARBALL_PATH ]; then
echo "Hermes tarball not present ($TARBALL_PATH). Build Hermes from source."
exit 0
fi
echo "Found Hermes tarball at $TARBALL_PATH"
echo "HERMES_ENGINE_TARBALL_PATH=$TARBALL_PATH" >> $GITHUB_ENV
- name: Print Hermes version
shell: bash
run: |
HERMES_TARBALL_ARTIFACTS_DIR=${{ inputs.hermes-tarball-artifacts-dir }}
TARBALL_FILENAME=$(node ./packages/react-native/scripts/hermes/get-tarball-name.js --buildType "${{ inputs.flavor }}")
TARBALL_PATH=$HERMES_TARBALL_ARTIFACTS_DIR/$TARBALL_FILENAME
if [[ -e $TARBALL_PATH ]]; then
tar -xf $TARBALL_PATH
echo 'print(HermesInternal?.getRuntimeProperties?.()["OSS Release Version"])' > test.js
chmod +x ./destroot/bin/hermes
./destroot/bin/hermes test.js
rm test.js
rm -rf destroot
else
echo 'No Hermes tarball found.'
fi
- name: Download ReactNativeDependencies
uses: actions/download-artifact@v4
with:
@@ -61,6 +105,7 @@ runs:
- name: Install CocoaPods dependencies
shell: bash
run: |
export HERMES_ENGINE_TARBALL_PATH=$HERMES_ENGINE_TARBALL_PATH
export RCT_USE_LOCAL_RN_DEP="/tmp/third-party/ReactNativeDependencies${{ inputs.flavor }}.xcframework.tar.gz"
export RCT_TESTONLY_RNCORE_TARBALL_PATH="/tmp/ReactCore/ReactCore${{ inputs.flavor }}.xcframework.tar.gz"
@@ -71,7 +116,7 @@ runs:
cd packages/rn-tester
bundle install
bundle exec pod update hermes-engine --no-repo-update
bundle exec pod install
- name: Build RNTester
shell: bash
run: |
@@ -121,7 +121,7 @@ describe('Create Draft Release', () => {
});
describe('#_computeBody', () => {
it('computes body for release when no hermes versions are passed', async () => {
it('computes body for release', async () => {
const version = '0.77.1';
const changelog = `## v${version}
### Breaking Changes
@@ -134,83 +134,20 @@ describe('Create Draft Release', () => {
#### iOS
- [PR #3436](https://github.com/facebook/react-native/pull/3436) - Some other change
- [PR #3437](https://github.com/facebook/react-native/pull/3437) - Some other change`;
const body = _computeBody(changelog, version);
const body = _computeBody(version, changelog);
expect(body).toEqual(`${changelog}
---
Hermes dSYMS:
- [Debug](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${version}/hermes-ios-${version}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${version}/hermes-ios-${version}-hermes-framework-dSYM-release.tar.gz)
Hermes V1 dSYMS:
- [Debug](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${version}/hermes-ios-${version}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${version}/hermes-ios-${version}-hermes-framework-dSYM-release.tar.gz)
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-hermes-framework-dSYM-release.tar.gz)
ReactNativeDependencies dSYMs:
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-dependencies-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-dependencies-dSYM-release.tar.gz)
ReactNative Core dSYMs:
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-core-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-core-release.tar.gz)
---
You can file issues or pick requests against this release [here](https://github.com/reactwg/react-native-releases/issues/new/choose).
---
To help you upgrade to this version, you can use the [Upgrade Helper](https://react-native-community.github.io/upgrade-helper/) ⚛️.
---
View the whole changelog in the [CHANGELOG.md file](https://github.com/facebook/react-native/blob/main/CHANGELOG.md).`);
});
it('computes body for release when hermes versions are passed', async () => {
const version = '0.77.1';
const hermesVersion = '0.15.0';
const hermesV1Version = '250829098.0.2';
const changelog = `## v${version}
### Breaking Changes
- [PR #9012](https://github.com/facebook/react-native/pull/9012) - Some other change
#### Android
- [PR #3456](https://github.com/facebook/react-native/pull/3456) - Some other change
- [PR #3457](https://github.com/facebook/react-native/pull/3457) - Some other change
#### iOS
- [PR #3436](https://github.com/facebook/react-native/pull/3436) - Some other change
- [PR #3437](https://github.com/facebook/react-native/pull/3437) - Some other change`;
const body = _computeBody(
changelog,
version,
hermesVersion,
hermesV1Version,
);
expect(body).toEqual(`${changelog}
---
Hermes dSYMS:
- [Debug](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesVersion}/hermes-ios-${hermesVersion}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesVersion}/hermes-ios-${hermesVersion}-hermes-framework-dSYM-release.tar.gz)
Hermes V1 dSYMS:
- [Debug](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesV1Version}/hermes-ios-${hermesV1Version}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesV1Version}/hermes-ios-${hermesV1Version}-hermes-framework-dSYM-release.tar.gz)
ReactNativeDependencies dSYMs:
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-dependencies-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-dependencies-dSYM-release.tar.gz)
ReactNative Core dSYMs:
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-core-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-core-release.tar.gz)
---
You can file issues or pick requests against this release [here](https://github.com/reactwg/react-native-releases/issues/new/choose).
+5 -21
View File
@@ -40,29 +40,19 @@ function _extractChangelog(version) {
return changelog.slice(changelogStarts, changelogEnds).join('\n').trim();
}
function _computeBody(changelog, version, hermesVersion, hermesV1Version) {
hermesVersion = hermesVersion ?? version;
hermesV1Version = hermesV1Version ?? version;
function _computeBody(version, changelog) {
return `${changelog}
---
Hermes dSYMS:
- [Debug](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesVersion}/hermes-ios-${hermesVersion}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesVersion}/hermes-ios-${hermesVersion}-hermes-framework-dSYM-release.tar.gz)
Hermes V1 dSYMS:
- [Debug](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesV1Version}/hermes-ios-${hermesV1Version}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/hermes/hermes-ios/${hermesV1Version}/hermes-ios-${hermesV1Version}-hermes-framework-dSYM-release.tar.gz)
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-hermes-framework-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-hermes-framework-dSYM-release.tar.gz)
ReactNativeDependencies dSYMs:
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-dependencies-dSYM-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-dependencies-dSYM-release.tar.gz)
ReactNative Core dSYMs:
- [Debug](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-core-debug.tar.gz)
- [Release](https://repo1.maven.org/maven2/com/facebook/react/react-native-artifacts/${version}/react-native-artifacts-${version}-reactnative-core-release.tar.gz)
---
You can file issues or pick requests against this release [here](https://github.com/reactwg/react-native-releases/issues/new/choose).
@@ -123,13 +113,7 @@ function moveToChangelogBranch(version) {
run(`git checkout -b changelog/v${version}`);
}
async function createDraftRelease(
version,
latest,
token,
hermesVersion,
hermesV1Version,
) {
async function createDraftRelease(version, latest, token) {
if (version.startsWith('v')) {
version = version.substring(1);
}
@@ -137,7 +121,7 @@ async function createDraftRelease(
_verifyTagExists(version);
moveToChangelogBranch(version);
const changelog = _extractChangelog(version);
const body = _computeBody(changelog, version, hermesVersion, hermesV1Version);
const body = _computeBody(version, changelog);
const release = await _createDraftReleaseOnGitHub(
version,
body,
+1 -1
View File
@@ -162,7 +162,7 @@ async function main() {
console.info(`WORKING_DIRECTORY: ${WORKING_DIRECTORY}`);
console.info('==============================\n');
const simulatorName = 'iPhone 16 Pro';
const simulatorName = 'iPhone 15 Pro';
launchSimulator(simulatorName);
installAppOnSimulator(APP_PATH);
const udid = extractSimulatorUDID();
+2 -1
View File
@@ -10,6 +10,7 @@ jobs:
- name: Checkout
uses: actions/checkout@v4
with:
token: ${{ secrets.REACT_NATIVE_BOT_GITHUB_TOKEN }}
fetch-depth: 0
fetch-tags: true
- name: Install dependencies
@@ -21,7 +22,7 @@ jobs:
- name: Setup xcode
uses: ./.github/actions/setup-xcode
with:
platform: 'ios'
xcode-version: '16.2.0'
- name: Extract branch name
run: |
TAG="${{ github.ref_name }}";
+1 -10
View File
@@ -2,15 +2,6 @@ name: Create Draft Release
on:
workflow_call:
inputs:
hermesVersion:
required: false
type: string
description: The version of Hermes to use for this release (eg. 0.15.0). If not specified, it will use React Native Version
hermesV1Version:
required: false
type: string
description: The version of Hermes V1 to use for this release (eg. 250829098.0.2). If not specified, it will use React Native Version
jobs:
create-draft-release:
@@ -36,7 +27,7 @@ jobs:
const {createDraftRelease} = require('./.github/workflow-scripts/createDraftRelease.js');
const version = '${{ github.ref_name }}';
const {isLatest} = require('./.github/workflow-scripts/publishTemplate.js');
return (await createDraftRelease(version, isLatest(), '${{secrets.REACT_NATIVE_BOT_GITHUB_TOKEN}}', ${{ inputs.hermesVersion }}, ${{ inputs.hermesV1Version }})).id;
return (await createDraftRelease(version, isLatest(), '${{secrets.REACT_NATIVE_BOT_GITHUB_TOKEN}}')).id;
result-encoding: string
- name: Upload release assets for DotSlash
uses: actions/github-script@v6
-1
View File
@@ -19,7 +19,6 @@ on:
jobs:
create_release:
if: github.repository == 'facebook/react-native'
runs-on: ubuntu-latest
steps:
- name: Checkout
+2
View File
@@ -10,6 +10,7 @@ jobs:
- name: Checkout repository
uses: actions/checkout@v4
with:
token: ${{ secrets.REACT_NATIVE_BOT_GITHUB_TOKEN }}
fetch-depth: 0
fetch-tags: true
- name: Install dependencies
@@ -22,6 +23,7 @@ jobs:
- name: Generate Changelog
uses: actions/github-script@v6
with:
github-token: ${{ secrets.REACT_NATIVE_BOT_GITHUB_TOKEN }}
script: |
const {generateChangelog} = require('./.github/workflow-scripts/generateChangelog');
const version = '${{ github.ref_name }}';
+120 -5
View File
@@ -21,21 +21,130 @@ jobs:
echo "Setting release type to nightly"
echo "RELEASE_TYPE=nightly" >> $GITHUB_OUTPUT
prepare_hermes_workspace:
runs-on: ubuntu-latest
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_VERSION_FILE: packages/react-native/sdks/.hermesversion
outputs:
react-native-version: ${{ steps.prepare-hermes-workspace.outputs.react-native-version }}
hermes-version: ${{ steps.prepare-hermes-workspace.outputs.hermes-version }}
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Prepare Hermes Workspace
id: prepare-hermes-workspace
uses: ./.github/actions/prepare-hermes-workspace
with:
hermes-ws-dir: ${{ env.HERMES_WS_DIR }}
hermes-version-file: ${{ env.HERMES_VERSION_FILE }}
build_hermesc_apple:
runs-on: macos-14
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: /tmp/hermes
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Apple
uses: ./.github/actions/build-hermesc-apple
with:
hermes-version: ${{ needs.prepare_hermes_workspace.output.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.output.react-native-version }}
build_apple_slices_hermes:
runs-on: macos-14
needs: [build_hermesc_apple, prepare_hermes_workspace]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
HERMES_OSXBIN_ARTIFACTS_DIR: /tmp/hermes/osx-bin
IOS_DEPLOYMENT_TARGET: "15.1"
XROS_DEPLOYMENT_TARGET: "1.0"
MAC_DEPLOYMENT_TARGET: "10.15"
strategy:
fail-fast: false
matrix:
flavor: [Debug, Release]
slice: [macosx, iphoneos, iphonesimulator, appletvos, appletvsimulator, catalyst, xros, xrsimulator]
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build Slice
uses: ./.github/actions/build-apple-slices-hermes
with:
flavor: ${{ matrix.flavor }}
slice: ${{ matrix.slice}}
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_hermes_macos:
runs-on: macos-14
needs: [build_apple_slices_hermes, prepare_hermes_workspace]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
continue-on-error: true
strategy:
fail-fast: false
matrix:
flavor: [Debug, Release]
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build Hermes MacOS
uses: ./.github/actions/build-hermes-macos
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
flavor: ${{ matrix.flavor }}
prebuild_apple_dependencies:
if: github.repository == 'facebook/react-native'
uses: ./.github/workflows/prebuild-ios-dependencies.yml
secrets: inherit
prebuild_react_native_core:
uses: ./.github/workflows/prebuild-ios-core.yml
with:
use-hermes-nightly: true
secrets: inherit
needs: [prebuild_apple_dependencies]
needs: [prebuild_apple_dependencies, build_hermes_macos]
build_hermesc_linux:
runs-on: ubuntu-latest
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Linux
uses: ./.github/actions/build-hermesc-linux
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_hermesc_windows:
runs-on: windows-2025
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: 'C:\tmp\hermes'
HERMES_TARBALL_ARTIFACTS_DIR: 'C:\tmp\hermes\hermes-runtime-darwin'
HERMES_OSXBIN_ARTIFACTS_DIR: 'C:\tmp\hermes\osx-bin'
ICU_URL: "https://github.com/unicode-org/icu/releases/download/release-64-2/icu4c-64_2-Win64-MSVC2017.zip"
MSBUILD_DIR: 'C:\Program Files (x86)\Microsoft Visual Studio\2019\BuildTools\MSBuild\Current\Bin'
CMAKE_DIR: 'C:\Program Files\CMake\bin'
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Windows
uses: ./.github/actions/build-hermesc-windows
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_android:
runs-on: 8-core-ubuntu
if: github.repository == 'facebook/react-native'
needs: [set_release_type]
container:
image: reactnativecommunity/react-native-android:latest
@@ -60,6 +169,10 @@ jobs:
needs:
[
set_release_type,
prepare_hermes_workspace,
build_hermes_macos,
build_hermesc_linux,
build_hermesc_windows,
build_android,
prebuild_apple_dependencies,
prebuild_react_native_core,
@@ -72,6 +185,7 @@ jobs:
# By default we only build ARM64 to save time/resources. For release/nightlies, we override this value to build all archs.
ORG_GRADLE_PROJECT_reactNativeArchitectures: "arm64-v8a"
env:
HERMES_WS_DIR: /tmp/hermes
GHA_NPM_TOKEN: ${{ secrets.GHA_NPM_TOKEN }}
ORG_GRADLE_PROJECT_SIGNING_PWD: ${{ secrets.ORG_GRADLE_PROJECT_SIGNING_PWD }}
ORG_GRADLE_PROJECT_SIGNING_KEY: ${{ secrets.ORG_GRADLE_PROJECT_SIGNING_KEY }}
@@ -83,6 +197,7 @@ jobs:
- name: Build and Publish NPM Package
uses: ./.github/actions/build-npm-package
with:
hermes-ws-dir: ${{ env.HERMES_WS_DIR }}
release-type: ${{ needs.set_release_type.outputs.RELEASE_TYPE }}
gha-npm-token: ${{ env.GHA_NPM_TOKEN }}
gradle-cache-encryption-key: ${{ secrets.GRADLE_CACHE_ENCRYPTION_KEY }}
+30 -16
View File
@@ -2,16 +2,11 @@ name: Prebuild iOS Dependencies
on:
workflow_call: # this directive allow us to call this workflow from other workflows
inputs:
use-hermes-nightly:
description: 'Whether to use the hermes nightly build or read the version from the versions.properties file'
type: boolean
required: false
default: false
jobs:
build-rn-slice:
runs-on: macos-15
runs-on: macos-14
strategy:
fail-fast: false
matrix:
@@ -37,20 +32,39 @@ jobs:
if: steps.restore-ios-slice.outputs.cache-hit != 'true'
uses: ./.github/actions/setup-xcode
with:
platform: ${{ matrix.slice }}
xcode-version: '16.2.0'
- name: Yarn Install
if: steps.restore-ios-slice.outputs.cache-hit != 'true'
uses: ./.github/actions/yarn-install
- name: Set Hermes version
- name: Download Hermes
if: steps.restore-ios-slice.outputs.cache-hit != 'true'
uses: actions/download-artifact@v4
with:
name: hermes-darwin-bin-${{ matrix.flavor }}
path: /tmp/hermes/hermes-runtime-darwin
- name: Extract Hermes
if: steps.restore-ios-slice.outputs.cache-hit != 'true'
shell: bash
run: |
if [ "${{ inputs.use-hermes-nightly }}" == "true" ]; then
HERMES_VERSION="nightly"
else
HERMES_VERSION=$(sed -n 's/^HERMES_VERSION_NAME=//p' packages/react-native/sdks/hermes-engine/version.properties)
HERMES_TARBALL_ARTIFACTS_DIR=/tmp/hermes/hermes-runtime-darwin
if [ ! -d $HERMES_TARBALL_ARTIFACTS_DIR ]; then
echo "Hermes tarball artifacts dir not present ($HERMES_TARBALL_ARTIFACTS_DIR)."
exit 0
fi
echo "Using Hermes version: $HERMES_VERSION"
echo "HERMES_VERSION=$HERMES_VERSION" >> $GITHUB_ENV
TARBALL_FILENAME=$(node ./packages/react-native/scripts/hermes/get-tarball-name.js --buildType "${{ matrix.flavor }}")
TARBALL_PATH=$HERMES_TARBALL_ARTIFACTS_DIR/$TARBALL_FILENAME
echo "Looking for $TARBALL_FILENAME in $HERMES_TARBALL_ARTIFACTS_DIR"
echo "$TARBALL_PATH"
if [ ! -f $TARBALL_PATH ]; then
echo "Hermes tarball not present ($TARBALL_PATH). Build Hermes from source."
exit 0
fi
echo "Found Hermes tarball at $TARBALL_PATH"
echo "HERMES_ENGINE_TARBALL_PATH=$TARBALL_PATH" >> $GITHUB_ENV
- name: Download ReactNativeDependencies
uses: actions/download-artifact@v4
with:
@@ -109,7 +123,7 @@ jobs:
packages/react-native/.build/headers
compose-xcframework:
runs-on: macos-15
runs-on: macos-14
needs: [build-rn-slice]
strategy:
fail-fast: false
+21 -15
View File
@@ -7,7 +7,7 @@ on:
jobs:
prepare_workspace:
name: Prepare workspace
runs-on: macos-15
runs-on: macos-14
steps:
- name: Checkout
uses: actions/checkout@v4
@@ -18,7 +18,7 @@ jobs:
uses: actions/cache/restore@v4
with:
path: packages/react-native/third-party/
key: v3-ios-dependencies-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
key: v2-ios-dependencies-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
enableCrossOsArchive: true
- name: Yarn Install
if: steps.restore-ios-prebuilds.outputs.cache-hit != 'true'
@@ -40,13 +40,13 @@ jobs:
uses: actions/cache/save@v4
if: ${{ github.ref == 'refs/heads/main' }} # To avoid that the cache explode
with:
key: v3-ios-dependencies-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
key: v2-ios-dependencies-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
enableCrossOsArchive: true
path: packages/react-native/third-party/
build-apple-slices:
name: Build Apple Slice
runs-on: macos-15
runs-on: macos-14
needs: [prepare_workspace]
strategy:
fail-fast: false
@@ -65,17 +65,16 @@ jobs:
uses: actions/checkout@v4
- name: Setup node.js
uses: ./.github/actions/setup-node
- name: Setup xcode
uses: ./.github/actions/setup-xcode
with:
xcode-version: '16.1'
- name: Restore slice folder
id: restore-slice-folder
uses: actions/cache/restore@v4
with:
path: packages/react-native/third-party/.build/Build/Products
key: v3-ios-dependencies-slice-folder-${{ matrix.slice }}-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
- name: Setup xcode
if: steps.restore-slice-folder.outputs.cache-hit != 'true'
uses: ./.github/actions/setup-xcode
with:
platform: ${{ matrix.slice }}
key: v2-ios-dependencies-slice-folder-${{ matrix.slice }}-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
- name: Yarn Install
if: steps.restore-slice-folder.outputs.cache-hit != 'true'
uses: ./.github/actions/yarn-install
@@ -86,8 +85,15 @@ jobs:
name: ios-prebuilds-workspace
path: packages/react-native/third-party/
- name: Print third-party folder structure
if: steps.restore-slice-folder.outputs.cache-hit != 'true'
run: ls -lR packages/react-native/third-party
- name: Install VisionOS
if: ${{ steps.restore-slice-folder.outputs.cache-hit != 'true' && (matrix.slice == 'xros' || matrix.slice == 'xros-simulator') }}
run: |
# https://github.com/actions/runner-images/issues/10559
sudo xcodebuild -runFirstLaunch
sudo xcrun simctl list
sudo xcodebuild -downloadPlatform visionOS
sudo xcodebuild -runFirstLaunch
- name: Build slice ${{ matrix.slice }} for ${{ matrix.flavor }}
if: steps.restore-slice-folder.outputs.cache-hit != 'true'
run: node scripts/releases/prepare-ios-prebuilds.js -b -p ${{ matrix.slice }} -r ${{ matrix.flavor }}
@@ -101,14 +107,14 @@ jobs:
uses: actions/cache/save@v4
if: ${{ github.ref == 'refs/heads/main' }} # To avoid that the cache explode
with:
key: v3-ios-dependencies-slice-folder-${{ matrix.slice }}-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
key: v2-ios-dependencies-slice-folder-${{ matrix.slice }}-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
enableCrossOsArchive: true
path: |
packages/react-native/third-party/.build/Build/Products
create-xcframework:
name: Prepare XCFramework
runs-on: macos-15
runs-on: macos-14
needs: [build-apple-slices]
strategy:
fail-fast: false
@@ -132,7 +138,7 @@ jobs:
with:
path: |
packages/react-native/third-party/
key: v3-ios-dependencies-xcframework-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
key: v2-ios-dependencies-xcframework-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
# If cache hit, we already have our binary. We don't need to do anything.
- name: Yarn Install
if: steps.restore-xcframework.outputs.cache-hit != 'true'
@@ -194,4 +200,4 @@ jobs:
path: |
packages/react-native/third-party/ReactNativeDependencies${{ matrix.flavor }}.xcframework.tar.gz
packages/react-native/third-party/ReactNativeDependencies${{ matrix.flavor }}.framework.dSYM.tar.gz
key: v3-ios-dependencies-xcframework-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
key: v2-ios-dependencies-xcframework-${{ matrix.flavor }}-${{ hashfiles('scripts/releases/ios-prebuild/configuration.js') }}
@@ -9,7 +9,6 @@ on:
jobs:
publish_bumped_packages:
runs-on: ubuntu-latest
if: github.repository == 'facebook/react-native'
env:
GHA_NPM_TOKEN: ${{ secrets.GHA_NPM_TOKEN }}
steps:
+113 -21
View File
@@ -19,43 +19,136 @@ jobs:
echo "Setting release type to release"
echo "RELEASE_TYPE=release" >> $GITHUB_OUTPUT
set_hermes_versions:
prepare_hermes_workspace:
runs-on: ubuntu-latest
if: github.repository == 'facebook/react-native'
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_VERSION_FILE: packages/react-native/sdks/.hermesversion
outputs:
HERMES_VERSION: ${{ steps.set_hermes_versions.outputs.HERMES_VERSION }}
HERMES_V1_VERSION: ${{ steps.set_hermes_versions.outputs.HERMES_V1_VERSION }}
react-native-version: ${{ steps.prepare-hermes-workspace.outputs.react-native-version }}
hermes-version: ${{ steps.prepare-hermes-workspace.outputs.hermes-version }}
steps:
- name: Checkout
uses: actions/checkout@v4
- id: set_hermes_versions
run: |
echo "Setting hermes versions to latest"
hermes_version=$(grep -oE 'HERMES_VERSION_NAME=([0-9]+\.[0-9]+\.[0-9]+)' packages/react-native/sdks/hermes-engine/version.properties | cut -d'=' -f2)
hermes_v1_version=$(grep -oE 'HERMES_V1_VERSION_NAME=([0-9]+\.[0-9]+\.[0-9]+)' packages/react-native/sdks/hermes-engine/version.properties | cut -d'=' -f2)
- name: Prepare Hermes Workspace
id: prepare-hermes-workspace
uses: ./.github/actions/prepare-hermes-workspace
with:
hermes-ws-dir: ${{ env.HERMES_WS_DIR }}
hermes-version-file: ${{ env.HERMES_VERSION_FILE }}
echo "HERMES_VERSION=$hermes_version" >> $GITHUB_OUTPUT
echo "HERMES_V1_VERSION=$hermes_v1_version" >> $GITHUB_OUTPUT
- name: Print hermes versions
run: |
echo "HERMES_VERSION=${{ steps.set_hermes_versions.outputs.HERMES_VERSION }}"
echo "HERMES_V1_VERSION=${{ steps.set_hermes_versions.outputs.HERMES_V1_VERSION }}"
build_hermesc_apple:
runs-on: macos-14
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: /tmp/hermes
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Apple
uses: ./.github/actions/build-hermesc-apple
with:
hermes-version: ${{ needs.prepare_hermes_workspace.output.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.output.react-native-version }}
build_apple_slices_hermes:
runs-on: macos-14
needs: [build_hermesc_apple, prepare_hermes_workspace]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
HERMES_OSXBIN_ARTIFACTS_DIR: /tmp/hermes/osx-bin
IOS_DEPLOYMENT_TARGET: "15.1"
XROS_DEPLOYMENT_TARGET: "1.0"
MAC_DEPLOYMENT_TARGET: "10.15"
strategy:
fail-fast: false
matrix:
flavor: [Debug, Release]
slice: [macosx, iphoneos, iphonesimulator, appletvos, appletvsimulator, catalyst, xros, xrsimulator]
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build Slice
uses: ./.github/actions/build-apple-slices-hermes
with:
flavor: ${{ matrix.flavor }}
slice: ${{ matrix.slice}}
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_hermes_macos:
runs-on: macos-14
needs: [build_apple_slices_hermes, prepare_hermes_workspace]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
continue-on-error: true
strategy:
fail-fast: false
matrix:
flavor: [Debug, Release]
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build Hermes MacOS
uses: ./.github/actions/build-hermes-macos
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
flavor: ${{ matrix.flavor }}
prebuild_apple_dependencies:
if: github.repository == 'facebook/react-native'
uses: ./.github/workflows/prebuild-ios-dependencies.yml
secrets: inherit
prebuild_react_native_core:
uses: ./.github/workflows/prebuild-ios-core.yml
secrets: inherit
needs: [prebuild_apple_dependencies]
needs: [prebuild_apple_dependencies, build_hermes_macos]
build_hermesc_linux:
runs-on: ubuntu-latest
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Linux
uses: ./.github/actions/build-hermesc-linux
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_hermesc_windows:
runs-on: windows-2025
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: 'C:\tmp\hermes'
HERMES_TARBALL_ARTIFACTS_DIR: 'C:\tmp\hermes\hermes-runtime-darwin'
HERMES_OSXBIN_ARTIFACTS_DIR: 'C:\tmp\hermes\osx-bin'
ICU_URL: "https://github.com/unicode-org/icu/releases/download/release-64-2/icu4c-64_2-Win64-MSVC2017.zip"
MSBUILD_DIR: 'C:\Program Files (x86)\Microsoft Visual Studio\2019\BuildTools\MSBuild\Current\Bin'
CMAKE_DIR: 'C:\Program Files\CMake\bin'
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Windows
uses: ./.github/actions/build-hermesc-windows
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_npm_package:
runs-on: 8-core-ubuntu
needs:
[
set_release_type,
prepare_hermes_workspace,
build_hermes_macos,
build_hermesc_linux,
build_hermesc_windows,
prebuild_apple_dependencies,
prebuild_react_native_core,
]
@@ -67,6 +160,7 @@ jobs:
# By default we only build ARM64 to save time/resources. For release/nightlies, we override this value to build all archs.
ORG_GRADLE_PROJECT_reactNativeArchitectures: "arm64-v8a"
env:
HERMES_WS_DIR: /tmp/hermes
GHA_NPM_TOKEN: ${{ secrets.GHA_NPM_TOKEN }}
ORG_GRADLE_PROJECT_SIGNING_PWD: ${{ secrets.ORG_GRADLE_PROJECT_SIGNING_PWD }}
ORG_GRADLE_PROJECT_SIGNING_KEY: ${{ secrets.ORG_GRADLE_PROJECT_SIGNING_KEY }}
@@ -82,6 +176,7 @@ jobs:
- name: Build and Publish NPM Package
uses: ./.github/actions/build-npm-package
with:
hermes-ws-dir: ${{ env.HERMES_WS_DIR }}
release-type: ${{ needs.set_release_type.outputs.RELEASE_TYPE }}
gha-npm-token: ${{ env.GHA_NPM_TOKEN }}
gradle-cache-encryption-key: ${{ secrets.GRADLE_CACHE_ENCRYPTION_KEY }}
@@ -139,9 +234,6 @@ jobs:
secrets: inherit
create_draft_release:
needs: [generate_changelog, set_hermes_versions]
needs: generate_changelog
uses: ./.github/workflows/create-draft-release.yml
secrets: inherit
with:
hermesVersion: ${{ needs.set_hermes_versions.outputs.HERMES_VERSION }}
hermesV1Version: ${{ needs.set_hermes_versions.outputs.HERMES_V1_VERSION }}
-1
View File
@@ -9,7 +9,6 @@ on:
jobs:
rerun:
runs-on: ubuntu-latest
if: github.repository == 'facebook/react-native'
steps:
- name: rerun ${{ inputs.run_id }}
env:
+164 -29
View File
@@ -11,7 +11,6 @@ on:
jobs:
set_release_type:
runs-on: ubuntu-latest
if: github.repository == 'facebook/react-native'
outputs:
RELEASE_TYPE: ${{ steps.set_release_type.outputs.RELEASE_TYPE }}
env:
@@ -33,22 +32,101 @@ jobs:
echo "Should I run E2E tests? ${{ inputs.run-e2e-tests }}"
prepare_hermes_workspace:
runs-on: ubuntu-latest
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_VERSION_FILE: packages/react-native/sdks/.hermesversion
outputs:
react-native-version: ${{ steps.prepare-hermes-workspace.outputs.react-native-version }}
hermes-version: ${{ steps.prepare-hermes-workspace.outputs.hermes-version }}
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Prepare Hermes Workspace
id: prepare-hermes-workspace
uses: ./.github/actions/prepare-hermes-workspace
with:
hermes-ws-dir: ${{ env.HERMES_WS_DIR }}
hermes-version-file: ${{ env.HERMES_VERSION_FILE }}
build_hermesc_apple:
runs-on: macos-14
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: /tmp/hermes
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Apple
uses: ./.github/actions/build-hermesc-apple
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_apple_slices_hermes:
runs-on: macos-14
needs: [build_hermesc_apple, prepare_hermes_workspace]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
HERMES_OSXBIN_ARTIFACTS_DIR: /tmp/hermes/osx-bin
IOS_DEPLOYMENT_TARGET: "15.1"
XROS_DEPLOYMENT_TARGET: "1.0"
MAC_DEPLOYMENT_TARGET: "10.15"
strategy:
fail-fast: false
matrix:
flavor: [Debug, Release]
slice: [macosx, iphoneos, iphonesimulator, appletvos, appletvsimulator, catalyst, xros, xrsimulator]
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build Slice
uses: ./.github/actions/build-apple-slices-hermes
with:
flavor: ${{ matrix.flavor }}
slice: ${{ matrix.slice}}
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_hermes_macos:
runs-on: macos-14
needs: [build_apple_slices_hermes, prepare_hermes_workspace]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
continue-on-error: true
strategy:
fail-fast: false
matrix:
flavor: [Debug, Release]
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build Hermes MacOS
uses: ./.github/actions/build-hermes-macos
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
flavor: ${{ matrix.flavor }}
prebuild_apple_dependencies:
if: github.repository == 'facebook/react-native'
uses: ./.github/workflows/prebuild-ios-dependencies.yml
secrets: inherit
prebuild_react_native_core:
uses: ./.github/workflows/prebuild-ios-core.yml
with:
use-hermes-nightly: ${{ !endsWith(github.ref_name, '-stable') }}
secrets: inherit
needs: [prebuild_apple_dependencies]
needs: [prebuild_apple_dependencies, build_hermes_macos]
test_ios_rntester_ruby_3_2_0:
runs-on: macos-15
runs-on: macos-14
needs:
[prebuild_apple_dependencies, prebuild_react_native_core]
[build_apple_slices_hermes, prepare_hermes_workspace, build_hermes_macos, prebuild_apple_dependencies, prebuild_react_native_core]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
steps:
- name: Checkout
uses: actions/checkout@v4
@@ -56,12 +134,17 @@ jobs:
uses: ./.github/actions/test-ios-rntester
with:
ruby-version: "3.2.0"
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
flavor: Debug
test_ios_rntester:
runs-on: macos-15-large
runs-on: macos-14-large
needs:
[prebuild_apple_dependencies, prebuild_react_native_core]
[build_apple_slices_hermes, prepare_hermes_workspace, build_hermes_macos, prebuild_apple_dependencies, prebuild_react_native_core]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
continue-on-error: true
strategy:
fail-fast: false
@@ -75,12 +158,17 @@ jobs:
uses: ./.github/actions/test-ios-rntester
with:
use-frameworks: ${{ matrix.frameworks }}
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
flavor: ${{ matrix.flavor }}
test_e2e_ios_rntester:
runs-on: macos-15-large
runs-on: macos-14-large
needs:
[test_ios_rntester]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
strategy:
fail-fast: false
matrix:
@@ -99,8 +187,6 @@ jobs:
run: ls -lR /tmp/RNTesterBuild
- name: Setup xcode
uses: ./.github/actions/setup-xcode
with:
platform: ios
- name: Run E2E Tests
uses: ./.github/actions/maestro-ios
with:
@@ -110,8 +196,11 @@ jobs:
flavor: ${{ matrix.flavor }}
test_e2e_ios_templateapp:
runs-on: macos-15-large
runs-on: macos-14-large
needs: [build_npm_package, prebuild_apple_dependencies]
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
strategy:
fail-fast: false
matrix:
@@ -121,8 +210,6 @@ jobs:
uses: actions/checkout@v4
- name: Setup xcode
uses: ./.github/actions/setup-xcode
with:
platform: ios
- name: Setup node.js
uses: ./.github/actions/setup-node
- name: Run yarn
@@ -131,6 +218,11 @@ jobs:
uses: ruby/setup-ruby@v1
with:
ruby-version: 2.6.10
- name: Download Hermes
uses: actions/download-artifact@v4
with:
name: hermes-darwin-bin-${{matrix.flavor}}
path: /tmp/react-native-tmp
- name: Download React Native Package
uses: actions/download-artifact@v4
with:
@@ -164,6 +256,9 @@ jobs:
REACT_NATIVE_PKG=$(find /tmp/react-native-tmp -type f -name "*.tgz")
echo "React Native tgs is $REACT_NATIVE_PKG"
HERMES_PATH=$(find /tmp/react-native-tmp -type f -name "*.tar.gz")
echo "Hermes path is $HERMES_PATH"
# For stable branches, we want to use the stable branch of the template
# In all the other cases, we want to use "main"
BRANCH=${{ github.ref_name }}
@@ -180,7 +275,7 @@ jobs:
export RCT_USE_LOCAL_RN_DEP=/tmp/third-party/ReactNativeDependencies${{ matrix.flavor }}.xcframework.tar.gz
# Disable prebuilds for now, as they are causing issues with E2E tests for 0.82-stable branch
# export RCT_TESTONLY_RNCORE_TARBALL_PATH="/tmp/ReactCore/ReactCore${{ matrix.flavor }}.xcframework.tar.gz"
RCT_NEW_ARCH_ENABLED=$NEW_ARCH_ENABLED bundle exec pod install
HERMES_ENGINE_TARBALL_PATH=$HERMES_PATH RCT_NEW_ARCH_ENABLED=$NEW_ARCH_ENABLED bundle exec pod install
xcodebuild \
-scheme "RNTestProject" \
@@ -266,11 +361,27 @@ jobs:
flavor: ${{ matrix.flavor }}
working-directory: /tmp/RNTestProject
build_hermesc_linux:
runs-on: ubuntu-latest
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: /tmp/hermes
HERMES_TARBALL_ARTIFACTS_DIR: /tmp/hermes/hermes-runtime-darwin
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Linux
uses: ./.github/actions/build-hermesc-linux
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
run_fantom_tests:
runs-on: 8-core-ubuntu
needs: [set_release_type]
container:
image: reactnativecommunity/react-native-android:latest
# Version is pinned to v18.0 to unblock `run_fantom_tests` - see https://github.com/react-native-community/docker-android/pull/242#issuecomment-3280029122
image: reactnativecommunity/react-native-android:v18.0
env:
TERM: "dumb"
GRADLE_OPTS: "-Dorg.gradle.daemon=false"
@@ -285,6 +396,25 @@ jobs:
release-type: ${{ needs.set_release_type.outputs.RELEASE_TYPE }}
gradle-cache-encryption-key: ${{ secrets.GRADLE_CACHE_ENCRYPTION_KEY }}
build_hermesc_windows:
runs-on: windows-2025
needs: prepare_hermes_workspace
env:
HERMES_WS_DIR: 'C:\tmp\hermes'
HERMES_TARBALL_ARTIFACTS_DIR: 'C:\tmp\hermes\hermes-runtime-darwin'
HERMES_OSXBIN_ARTIFACTS_DIR: 'C:\tmp\hermes\osx-bin'
ICU_URL: "https://github.com/unicode-org/icu/releases/download/release-64-2/icu4c-64_2-Win64-MSVC2017.zip"
MSBUILD_DIR: 'C:\Program Files (x86)\Microsoft Visual Studio\2019\BuildTools\MSBuild\Current\Bin'
CMAKE_DIR: 'C:\Program Files\CMake\bin'
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build HermesC Windows
uses: ./.github/actions/build-hermesc-windows
with:
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
build_android:
runs-on: 8-core-ubuntu
needs: [set_release_type]
@@ -339,6 +469,10 @@ jobs:
needs:
[
set_release_type,
prepare_hermes_workspace,
build_hermes_macos,
build_hermesc_linux,
build_hermesc_windows,
build_android,
prebuild_apple_dependencies,
prebuild_react_native_core,
@@ -348,12 +482,15 @@ jobs:
env:
TERM: "dumb"
GRADLE_OPTS: "-Dorg.gradle.daemon=false"
env:
HERMES_WS_DIR: /tmp/hermes
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Build NPM Package
uses: ./.github/actions/build-npm-package
with:
hermes-ws-dir: ${{ env.HERMES_WS_DIR }}
release-type: ${{ needs.set_release_type.outputs.RELEASE_TYPE }}
gradle-cache-encryption-key: ${{ secrets.GRADLE_CACHE_ENCRYPTION_KEY }}
@@ -396,12 +533,6 @@ jobs:
cache-encryption-key: ${{ secrets.GRADLE_CACHE_ENCRYPTION_KEY }}
- name: Run yarn install
uses: ./.github/actions/yarn-install
- name: Set nightly Hermes versions
shell: bash
run: |
node ./scripts/releases/use-hermes-nightly.js
- name: Run yarn install again, with the correct hermes version
uses: ./.github/actions/yarn-install
- name: Prepare the Helloworld application
shell: bash
run: node ./scripts/e2e/init-project-e2e.js --useHelloWorld --pathToLocalReactNative "$GITHUB_WORKSPACE/build/$(cat build/react-native-package-version)"
@@ -422,10 +553,11 @@ jobs:
compression-level: 0
test_ios_helloworld_with_ruby_3_2_0:
runs-on: macos-15
needs: [prebuild_apple_dependencies, prebuild_react_native_core]
runs-on: macos-14
needs: [prepare_hermes_workspace, build_hermes_macos, prebuild_apple_dependencies, prebuild_react_native_core] # prepare_hermes_workspace must be there because we need its reference to retrieve a couple of outputs
env:
PROJECT_NAME: iOSTemplateProject
HERMES_WS_DIR: /tmp/hermes
YARN_ENABLE_IMMUTABLE_INSTALLS: false
steps:
- name: Checkout
@@ -434,10 +566,12 @@ jobs:
with:
ruby-version: 3.2.0
flavor: Debug
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
test_ios_helloworld:
runs-on: macos-15
needs: [prebuild_apple_dependencies, prebuild_react_native_core]
runs-on: macos-14
needs: [prepare_hermes_workspace, build_hermes_macos, prebuild_apple_dependencies, prebuild_react_native_core] # prepare_hermes_workspace must be there because we need its reference to retrieve a couple of outputs
strategy:
matrix:
flavor: [Debug, Release]
@@ -448,6 +582,7 @@ jobs:
use_frameworks: StaticLibraries
env:
PROJECT_NAME: iOSTemplateProject
HERMES_WS_DIR: /tmp/hermes
YARN_ENABLE_IMMUTABLE_INSTALLS: false
steps:
- name: Checkout
@@ -456,10 +591,11 @@ jobs:
with:
flavor: ${{ matrix.flavor }}
use-frameworks: ${{ matrix.use_frameworks }}
hermes-version: ${{ needs.prepare_hermes_workspace.outputs.hermes-version }}
react-native-version: ${{ needs.prepare_hermes_workspace.outputs.react-native-version }}
test_js:
runs-on: ubuntu-latest
if: github.repository == 'facebook/react-native'
strategy:
fail-fast: false
matrix:
@@ -474,7 +610,6 @@ jobs:
lint:
runs-on: ubuntu-latest
if: github.repository == 'facebook/react-native'
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
steps:
@@ -27,7 +27,6 @@ on:
jobs:
validate-dotslash-artifacts:
runs-on: ubuntu-latest
if: github.repository == 'facebook/react-native'
steps:
- name: Checkout repository
uses: actions/checkout@v4
-1
View File
@@ -133,7 +133,6 @@ vendor/
# Swift Package build folder
/packages/react-native/.build
/packages/react-native/.swiftpm
/packages/react-native/React/includes/
# @react-native/codegen
/packages/react-native/React/FBReactNativeSpec/
-9
View File
@@ -1,14 +1,5 @@
# Changelog (pre 0.80)
## v0.79.7
### Fixed
#### Android specific
- **Layout:** Make missing parent view state in updateLayout a soft error ([56ad8d9bfd](https://github.com/facebook/react-native/commit/56ad8d9bfd08ea70bc6f5726a2b4a6afb6d2d7c2) by [@javache](https://github.com/javache))
- **Layout:** Make missing parent view state in updateLayout a soft error ([f2e47d8dab](https://github.com/facebook/react-native/commit/f2e47d8dabcd61621ea81c86cd1e2488948c4229) by [@cipolleschi](https://github.com/cipolleschi))
## v0.79.6
### Added
+2 -247
View File
@@ -1,248 +1,5 @@
# Changelog
## v0.82.1
### Fixed
#### Android specific
- Fixed representation of transforms when view is originally zero-sized ([a81e94a40c](https://github.com/facebook/react-native/commit/a81e94a40ca8dca9e57b562db21f8f235c5b25a0) by [@javache](https://github.com/javache))
#### iOS specific
- Fixed issue when using gnu coreutils cp command when using precompiled binaries causing compilation error ([068ec39aea](https://github.com/facebook/react-native/commit/068ec39aea543617e5159fe22274b294bfb29026) by [@chrfalch](https://github.com/chrfalch))
## v0.82.0
### Breaking
- **Appearance.setColorScheme:** `Appearance.setColorScheme` no longer accepts a nullable value ([a4581ecd8b](https://github.com/facebook/react-native/commit/a4581ecd8b6df5efa44dfe6d43708320209c900b) by [@huntie](https://github.com/huntie))
- **`CxxSharedModuleWrapper`:** Removed CxxSharedModuleWrapper ([fafbee2402](https://github.com/facebook/react-native/commit/fafbee240235ea0e63eb01abd31ce32d6a576429) by [@javache](https://github.com/javache))
- **DOM API:** Enable DOM APIs in host component refs ([2ad845ccb2](https://github.com/facebook/react-native/commit/2ad845ccb2fea277e05513dcf41407026a8224f0) by [@rubennorte](https://github.com/rubennorte))
- **Error Handling:** Unhandled promises are now handled by ExceptionsManager.handleException, instead of being swallowed as Logbox Warnings. ([c4082c9ce2](https://github.com/facebook/react-native/commit/c4082c9ce208a324c2d011823ca2ba432411aafc) by [@krystofwoldrich](https://github.com/krystofwoldrich))
- **InteractionManager:** InteractionManager has been deprecated and no longer respects interaction handles. Instead, it is now recommended to avoid executing long-running JavaScript tasks by breaking them up into smaller tasks and scheduling them using `requestIdleCallback()`. ([03d9f34a82](https://github.com/facebook/react-native/commit/03d9f34a8252456d389d9f9a3bd04b99a2828c16) by [@yungsters](https://github.com/yungsters))
- **`shouldEmitW3CPointerEvents`:** Migrate `shouldPressibilityUseW3CPointerEventsForHover` to common private feature flags and remove `shouldEmitW3CPointerEvents` flag. ([fb4587780e](https://github.com/facebook/react-native/commit/fb4587780e8d6111139d73598a9a26ff392dee28) by [@coado](https://github.com/coado))
- **TurboModuleUtils:** Remove unused ReactCommon/TurboModuleUtils functions #deepCopyJSIObject and #deepCopyJSIArray ([ead669ade3](https://github.com/facebook/react-native/commit/ead669ade31ee703c407f96c0ce98d8f2991bdc8) by [@christophpurrer](https://github.com/christophpurrer))
- **TurboModules:** Delete old location of CallbackWrapper.h / LongLivedObject.h by ([cb94e71](https://github.com/facebook/react-native/commit/cb94e71845259ae7fa823eb4d21cde74fccd7435) [@christophpurrer](https://github.com/christophpurrer))
#### Android specific
- **Deps:** Gradle to 9.0 ([7f93b664b4](https://github.com/facebook/react-native/commit/7f93b664b41ba11226aae7cca0e7c9b7f38a7d18) by [@cortinico](https://github.com/cortinico))
- **Image Prefetching:** Android: Image Prefetching send ImageResizeMode as enum value ([e30f34eda6](https://github.com/facebook/react-native/commit/e30f34eda689994cab8cd62aa38175238da8638b) by [@christophpurrer](https://github.com/christophpurrer))
- **New Architecture:** Remove possibility to newArchEnabled=false in 0.82 ([d5d21d0614](https://github.com/facebook/react-native/commit/d5d21d061493ee973c789a7c6ab8cceebc1f04f9) by [@cortinico](https://github.com/cortinico))
- **`reactNativeHost`:** Throw Exception if ReactApplication.reactNativeHost is not overriden ([0d3791ca0a](https://github.com/facebook/react-native/commit/0d3791ca0ab30d5a12881c9901f31291b3e998c6) by [@mdvacca](https://github.com/mdvacca))
- **ViewManagerInterfaces:** Migrate ViewManagerInterfaces to kotlin. Some types in code generated ViewManagerInterfaces might differ. e.g. this will start enforcing nullability in parameters of viewManagerInterface methods (e.g. String commands parameters are not nullable, view params are not nullable in any method, etc) ([79ca9036d3](https://github.com/facebook/react-native/commit/79ca9036d39c16cd115dc0427cb7092f358ac47e) by [@mdvacca](https://github.com/mdvacca))
#### iOS Specific
- **New Architecture:** Removed the opt-out from the New Architecture. ([83e6eaf693](https://github.com/facebook/react-native/commit/83e6eaf693f967b7870a5d4896cbb799206a14f0) by [@cipolleschi](https://github.com/cipolleschi))
### Added
- **Animated:** `Animated.CompositeAnimation` is now exposed when using `"react-native-strict-api"` ([024d25794a](https://github.com/facebook/react-native/commit/024d25794a51c94c877c1dfa115a82ebbf559614) by [@huntie](https://github.com/huntie))
- **Animated:** Allow calling createAnimatedNode without batching ([d9d9a49e18](https://github.com/facebook/react-native/commit/d9d9a49e18f3c51caa18cf7da0a1fcd62f1ecf18) by [@zeyap](https://github.com/zeyap))
- **Animated:** Allow filter usage with native animated driver. ([138d0eb01d](https://github.com/facebook/react-native/commit/138d0eb01dbe597261459a37d364d1780c3ef228) by [@intergalacticspacehighway](https://github.com/intergalacticspacehighway))
- **API:** Expose NativeComponentRegistry API as JavaScript root export ([f936780cd5](https://github.com/facebook/react-native/commit/f936780cd5c0c17797f9d2bbc8f5cee81c2eefce) by [@zhongwuzw](https://github.com/zhongwuzw))
- **API:** Expose `ReactNativeVersion` API as JavaScript root export ([ec5638abd0](https://github.com/facebook/react-native/commit/ec5638abd0e872be62b6ea5d8df9bed6335c2191) by [@huntie](https://github.com/huntie))
- **Codegen:** Added getDebugProps to codegen ([e547f466ee](https://github.com/facebook/react-native/commit/e547f466ee41415a75ec6b6f910171285ee7bfc3) by [@cipolleschi](https://github.com/cipolleschi))
- **Hermes V1:** Added a dependency on hermes-compiler ([0caf8e70d5](https://github.com/facebook/react-native/commit/0caf8e70d53f611a73ad9b55879dfe0a5f036371) by [@j-piasecki](https://github.com/j-piasecki))
- **Pressable:** Allow setting `blockNativeResponder` on Pressable ([6e4d23ded2](https://github.com/facebook/react-native/commit/6e4d23ded2da4a717bafcc032e3d7a0a5fbe3731) by [@zeyap](https://github.com/zeyap))
- **Yoga/API:** Make yoga/Yoga.h an umbrell header ([8ed2cee80e](https://github.com/facebook/react-native/commit/8ed2cee80e0aaac2f2a6a897ba450888f274a5a4) by [@rudybear](https://github.com/rudybear))
#### Android specific
- **Build Type:** Create a `debugOptimized` `buildType` for Android ([eb2461c7c9](https://github.com/facebook/react-native/commit/eb2461c7c902ebed272bd2d22d6cff4d3c586da6) by [@cortinico](https://github.com/cortinico))
- **DevMenu:** Add long-press back as an option to open the DevMenu for devices that lack menu & fast-forward. ([32d37f03ad](https://github.com/facebook/react-native/commit/32d37f03ad05290205a4f04d756f6e1880c4ff89) by [@sbuggay](https://github.com/sbuggay))
- **DevTools:** `DevSupportManager::openDebugger` now supports an optional `panel` param determining the starting panel ([7eb3536728](https://github.com/facebook/react-native/commit/7eb3536728c4a20f7e51245f4f7b64aa505bd799) by [@huntie](https://github.com/huntie))
- **DevTools:** Adds a landing view parameter to opening RNDT, enabling arbitrary view focus on launch. ([635c707eec](https://github.com/facebook/react-native/commit/635c707eec18f6d2ceceac2dcee9f458f17f8aab) by [@sbuggay](https://github.com/sbuggay))
- **Hermes V1:** Added opt-in to use the new Hermes ([3e9990f860](https://github.com/facebook/react-native/commit/3e9990f860eb9380837ef431ca02def32c4261ad) by [@j-piasecki](https://github.com/j-piasecki))
- **HWInput:** Channel up/down hardware events. ([c2a3e4420e](https://github.com/facebook/react-native/commit/c2a3e4420e07147f9a040a665da98dbe22b87a2a) by [@sbuggay](https://github.com/sbuggay))
- **Manifest:** Add support to specify a single Manifest rather than 2 (main/debug) by using the `usesCleartextTraffic` manifest placeholder which is autoconfigured by RNGP. ([d89acc1596](https://github.com/facebook/react-native/commit/d89acc1596345534882938d2bbf40275a6cb89bd) by [@cortinico](https://github.com/cortinico))
#### iOS specific
- **API:** Add deprecation message for RCTAppdelegate APIs ([d503ea4efc](https://github.com/facebook/react-native/commit/d503ea4efc84b6511cef2a46421a16e044862e88) by [@cipolleschi](https://github.com/cipolleschi))
- **Fabric:** Add invalidation callback for non-recycled component instances ([dc4a6d2c7e](https://github.com/facebook/react-native/commit/dc4a6d2c7e2ed421b61929896f60b1a864a60d97) by [@kkafar](https://github.com/kkafar))
- **Hermes V1:** Added opt-in to use the new Hermes ([e9cdc308b4](https://github.com/facebook/react-native/commit/e9cdc308b4c04753d85757e8877ac00c3c687b95) by [@j-piasecki](https://github.com/j-piasecki))
- **New Architecture:** Add warning if RCT_NEW_ARCH_ENABLED is set to 0 ([7d0bef2f25](https://github.com/facebook/react-native/commit/7d0bef2f25a206d917e7f5cc2b9a6c088f13a832) by [@cipolleschi](https://github.com/cipolleschi))
- **New Architecture:** Crash the app if they force the legacy architecture. ([dc132a4fd4](https://github.com/facebook/react-native/commit/dc132a4fd4ca8dc28dc7dbb2406ac67dac1a0ee7) by [@cipolleschi](https://github.com/cipolleschi))
### Changed
- **Font:** Enabled `enableFontScaleChangesUpdatingLayout` feature flag by default ([686d14f1d1](https://github.com/facebook/react-native/commit/686d14f1d16c2f02720104ddd395f7d27c908350) by [@j-piasecki](https://github.com/j-piasecki))
- **Hermes:** Changed names of hermes binaries ([776fca1e7c](https://github.com/facebook/react-native/commit/776fca1e7c978a2d8f817d042836073e4dcb4e0e) by [@j-piasecki](https://github.com/j-piasecki))
- **Hermes V1:** Changed the source of hermesc binary to be an npm package ([2e0bd13a25](https://github.com/facebook/react-native/commit/2e0bd13a2533fe7ab64125a95b9215b806018c6e) by [@j-piasecki](https://github.com/j-piasecki))
- **Metro:** Bump Metro to ^0.83.1 ([840fd6c83f](https://github.com/facebook/react-native/commit/840fd6c83f45326a796bf2823f8c2fa942aed06c) by [@robhogan](https://github.com/robhogan))
- **React:** Bumped React to 19.1.1 ([ec5a98b1f5](https://github.com/facebook/react-native/commit/ec5a98b1f5c2137f5f6ff5f5f6706f20384c44df) by [@cipolleschi](https://github.com/cipolleschi))
- **Runtime:** CDP backend now accepts `addBinding` and `removeBinding` methods earlier, before a Runtime exists. ([3271e57c75](https://github.com/facebook/react-native/commit/3271e57c751e7d1193c1e9f7b53e545231511b9d) by [@motiz88](https://github.com/motiz88))
- **Typing:** Update types for Platform.version ([f6ba2dbf3b](https://github.com/facebook/react-native/commit/f6ba2dbf3b4c85da1a7f9079fd366a41b160fa69) by [@riteshshukla04](https://github.com/riteshshukla04))
- **UIManager:** Avoid unnecessary copy of view props map in UIManager::updateShadowTree ([5b38bb4745](https://github.com/facebook/react-native/commit/5b38bb47457f853c2c3d5f275facbb9fbc150683) by [@zeyap](https://github.com/zeyap))
#### Android specific
- **AGP:** AGP to 8.12.0 ([742ef3d661](https://github.com/facebook/react-native/commit/742ef3d6615c8c1202e9f683e6127ac97d7a9e23) by [@cortinico](https://github.com/cortinico))
- **DevSupportManager:** DevSupport `openDebugger()` methods now accept a `panel: String?` param. Frameworks directly implementing `DevSupportManager` will need to adjust call signatures. ([9dba7112cf](https://github.com/facebook/react-native/commit/9dba7112cfd09b02300869a77dba3dca16f49a28) by [@huntie](https://github.com/huntie))
- **Kotlin:** Migrated TextAttributeProps to Kotlin. You might need to update your property access to use camelCase instead of Hungarian notation. ([fa921b3c7b](https://github.com/facebook/react-native/commit/fa921b3c7b289800a79196468f993a0eb0bf693f) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrated ReactBaseTextShadowNode to Kotlin. You might need to update your property access to use camelCase instead of Hungarian notation. ([8ccfff9a46](https://github.com/facebook/react-native/commit/8ccfff9a46f317fd78f478c8b3f180441535d1ca) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrated com.facebook.react.bridge.Arguments to Kotlin. ([2534aeaddb](https://github.com/facebook/react-native/commit/2534aeaddb0490b69dfaba6b8d316616c7e10a9c) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaConfig` to Kotlin ([4d5caef76b](https://github.com/facebook/react-native/commit/4d5caef76b83eb7e983364ecc81abb6027e5f98e) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaValue` to Kotlin ([4340dcbae8](https://github.com/facebook/react-native/commit/4340dcbae8fc41cde844e805a1ebfc23d23d164f) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaNative` to Kotlin ([bc54a06fcb](https://github.com/facebook/react-native/commit/bc54a06fcb5b5d1efd8996d8568733b657fc1b06) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaConfigFactory` to Kotlin ([33ca53d9db](https://github.com/facebook/react-native/commit/33ca53d9dbe53b92d65f82dbd53a2e9f23efd4f3) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `DoNotStrip` to Kotlin ([35d8086881](https://github.com/facebook/react-native/commit/35d8086881fac643b0ebc0d53aaf7e79b7ccd830) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaLayoutType` to Kotlin ([7e461003c6](https://github.com/facebook/react-native/commit/7e461003c6592c8c539960bd5e8169c48dd27f50) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `LayoutPassReason` to Kotlin ([db2a9c089c](https://github.com/facebook/react-native/commit/db2a9c089cd5802d99e0fc86e4dc0dbf7c888307) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaNodeFactory` to Kotlin ([40afa75a7c](https://github.com/facebook/react-native/commit/40afa75a7c816a5581223c7bcd1b65b8713edf47) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaMeasureOutput` to Kotlin ([453508ada8](https://github.com/facebook/react-native/commit/453508ada837554455733e3ca94440a7143f51b1) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaMeasureFunction` to Kotlin ([05eddd354e](https://github.com/facebook/react-native/commit/05eddd354e2e80ad3c95ed5a2199a59a77317891) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaStyleInputs` to Kotlin ([001736000f](https://github.com/facebook/react-native/commit/001736000f69ce98db86c17707408bbf3f0ae9a5) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaBaselineFunction` to Kotlin ([a2eb3b299d](https://github.com/facebook/react-native/commit/a2eb3b299dddea60c510821b662dfed55b334df7) by [@mateoguzmana](https://github.com/mateoguzmana))
- **Kotlin:** Migrate `YogaLogger` to Kotlin ([9c9a39b58e](https://github.com/facebook/react-native/commit/9c9a39b58e12bc734c27a5d9306e792b0dcaf927) by [@mateoguzmana](https://github.com/mateoguzmana))
- **OnBatchCompleteListener:** Make OnBatchCompleteListener interface internal ([046ff8e58b](https://github.com/facebook/react-native/commit/046ff8e58bed5da0f19adc860b327c7248b19f48) by [@cortinico](https://github.com/cortinico))
- **ReactSurface:** Changed return type of ReactSurfaceImpl.view to ReactSurfaceView to align with parameter recived by ReactSurfaceImpl.attachView() ([41029d8e91](https://github.com/facebook/react-native/commit/41029d8e91492c34c377374b442b31755874618c) by [@mdvacca](https://github.com/mdvacca))
- **TextAttributeProps:** Deprecate the field `TextAttributeProps.effectiveLineHeight`. This field was public but never used in OSS. ([ede037ade7](https://github.com/facebook/react-native/commit/ede037ade795bd44725f9bd82cace193a74aa68d) by [@cortinico](https://github.com/cortinico))
- **ViewManagers:** Changed method arguments names for Core ViewManagers to match the names of ViewManagerInterfaces ([e7d9e0d197](https://github.com/facebook/react-native/commit/e7d9e0d1977c136a85b9a78ef36a258631d1e9ba) by [@mdvacca](https://github.com/mdvacca))
### Deprecated
- **APIs:** Deprecate legacy javascript react native apis ([e7aeea26bd](https://github.com/facebook/react-native/commit/e7aeea26bde6e9cda0a3a0a55fc2a0421fb0c0e5) by [@RSNara](https://github.com/RSNara))
- **StyleSheet:** `StyleSheet.absoluteFillObject` is deprecated in favor of `StyleSheet.absoluteFill` (equivalent). ([83e19813ff](https://github.com/facebook/react-native/commit/83e19813ff5498ab3497d97fe38dba63a5554425) by [@huntie](https://github.com/huntie))
- Deprecate all the c++ classes not used by interop, or the new architecture. ([9539cd2626](https://github.com/facebook/react-native/commit/9539cd26261aef646379104833c7f719e3d83d02) by [@RSNara](https://github.com/RSNara))
#### Android specific
- **DevMenu:** Remove bridge mode string from React Native Dev Menu title ([1c838f32a9](https://github.com/facebook/react-native/commit/1c838f32a9bcee3867ec0502b344889308302f26) by [@sbuggay](https://github.com/sbuggay))
- **New Architecture:** DefaultDevSupportManagerFactory.create() method used for Old Arch ([026e22bb8d](https://github.com/facebook/react-native/commit/026e22bb8d7b38b3bd66ffcc7d4ee446adfee943) by [@cortinico](https://github.com/cortinico))
- **New Architecture:** Deprecate `BridgelessReactContext.getCatalystInstance()` method ([4583fbe052](https://github.com/facebook/react-native/commit/4583fbe052924df1ad030e51ad80e8d754a4c5a4) by [@cortinico](https://github.com/cortinico))
- **New Architecture:** Deprecate legacy architecture classes ReactInstanceManager and ReactInstanceManagerBuilder, these classes will be deleted in a future release ([fb84932e48](https://github.com/facebook/react-native/commit/fb84932e4894a45c0a2725e1d665acdf7bcea435) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Depreacate `CoreModulesPackage` and `NativeModuleRegistryBuilder` legacy architecture classes, these classes unused in the new architecture and will be deleted in the future ([d3bbbd893a](https://github.com/facebook/react-native/commit/d3bbbd893acd500237ab4e1778c6a2e0fe1948a9) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate Legacy Architecture ViewManagers, these classes are not used as part of the new architecture and will be deleted in the future ([da74d5da2c](https://github.com/facebook/react-native/commit/da74d5da2cac5306e37368c65490c434e7ff9f4f) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture ShadowNode classes included in React Native ([07091a9ae8](https://github.com/facebook/react-native/commit/07091a9ae8d70a601d969d9def4952563d3b7bcf) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Depreacte all LegacyArchitecture classes from the bridge package ([c1f7c5e321](https://github.com/facebook/react-native/commit/c1f7c5e3217a7e8a77a859652aadff2a41e3ea58) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture class UIManagerProvider ([b29b86f275](https://github.com/facebook/react-native/commit/b29b86f27553eac50daa18ffb6bca07be3f24f25) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate BridgeDevSupportManager and JSInstance ([25c011eb4d](https://github.com/facebook/react-native/commit/25c011eb4d403040b57e338bec704769de20793c) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate NativeModuleRegistry Legacy Architecture class ([22e4c25211](https://github.com/facebook/react-native/commit/22e4c252116da1a6658b15a84720e0ee314dddd6) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate subset of LegacyArchitecture classes in com/facebook/react/bridge ([78a3ff81eb](https://github.com/facebook/react-native/commit/78a3ff81eb38ae26fb15106580de841477897101) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture class FrescoBasedReactTextInlineImageShadowNode ([25f466cc4d](https://github.com/facebook/react-native/commit/25f466cc4dd28c962b967475c04c284d26efb722) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate Legacy Architecture class CallbackImpl ([718126fcf0](https://github.com/facebook/react-native/commit/718126fcf0296969ee659c31fae51b4317c896d3) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture class JavaMethodWrapper ([19a99dd088](https://github.com/facebook/react-native/commit/19a99dd0882d786daea3db486fd3aed3c10419b5) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate Legacy Architecture ShadowNode classes ([c4715886a9](https://github.com/facebook/react-native/commit/c4715886a917eb3eb63aab366de5225090dff5a1) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture UIManagerModules class ([85610c8b43](https://github.com/facebook/react-native/commit/85610c8b43ea132154cddcfed973ee6ceb3e55b3) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture classes from com/facebook/react/uimanager ([7f5b2b8f84](https://github.com/facebook/react-native/commit/7f5b2b8f84d7941891a447978c6adc17929ef87f) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture classes from package com.facebook.react.uimanager ([39d24bade3](https://github.com/facebook/react-native/commit/39d24bade317920544a3715e3a1f131663d8cded) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** Deprecate LegacyArchitecture classes from LayoutAnimation package ([f67078df07](https://github.com/facebook/react-native/commit/f67078df07b6c9ad995eb43ff47fc4a43bb2eaee) by [@mdvacca](https://github.com/mdvacca))
- **New Architecture:** ReactPackageLogger is not supported in the new architecture and being deprecated ([65671108f6](https://github.com/facebook/react-native/commit/65671108f69d9b23a011841102e4141293581d9c) by [@mdvacca](https://github.com/mdvacca))
#### iOS specific
- **DevMenu:** Remove bridge mode title and description from React Native Dev Menu title ([775daf5972](https://github.com/facebook/react-native/commit/775daf597280db94354ed484f2ce81690f1eb7b0) by [@sbuggay](https://github.com/sbuggay))
- **New Architecture:** Deprecate all the objc classes not used by interop, or the new architecture. ([70f53ac4ea](https://github.com/facebook/react-native/commit/70f53ac4ea144020560906f5931e480ed4dee87c) by [@RSNara](https://github.com/RSNara))
### Removed
- **New Architecture:** Core: Remove legacy components ([9c8a4c2297](https://github.com/facebook/react-native/commit/9c8a4c22973c7ce6fcf6b5d22c6d5fd4c6dc0d92) by [@RSNara](https://github.com/RSNara))
#### Android specific
- **DefaultReactHost:** Delete unused `DefaultReactHost.getDefaultReactHost()` overload ([d35ddb5e59](https://github.com/facebook/react-native/commit/d35ddb5e59a8cb990dd61a154a8e15e9542f8b15) by [@cortinico](https://github.com/cortinico))
- **DefaultReactHost:** Remove deprecated DefaultReactHost.getDefaultReactHost() overload - part 2 ([bda6acf3b0](https://github.com/facebook/react-native/commit/bda6acf3b08779c0dae7bdadbc9913eea79acd0d) by [@cortinico](https://github.com/cortinico))
- **DefaultReactHost:** Remove deprecated DefaultReactHost.getDefaultReactHost() overload - part 1 ([474f455a75](https://github.com/facebook/react-native/commit/474f455a7591049382da0d0308ddd21589f0cc7e) by [@cortinico](https://github.com/cortinico))
- **Inspector:** Removed unused `Inspector` public class from React Android ([cf528526cc](https://github.com/facebook/react-native/commit/cf528526cc375f1003125cf63f66fbd88790ceae) by [@cortinico](https://github.com/cortinico))
- **JSONArguments:** Remove the `com.facebook.react.bridge.JSONArguments` class ([04ae15d99b](https://github.com/facebook/react-native/commit/04ae15d99bb2ee6f7987bbe8c3d7acfdd46a482f) by [@cortinico](https://github.com/cortinico))
- **MessageQueueThreadPerfStats:** Deprecated MessageQueueThreadPerfStats API and replaced with stub. ([3bf5cb3d0e](https://github.com/facebook/react-native/commit/3bf5cb3d0e7d9d1749ef19a8392b9bbd3ec7ab7d) by [@javache](https://github.com/javache))
### Fixed
- **Accessibility:** Fix for setting the default value for accessibility props ([586f5ba89c](https://github.com/facebook/react-native/commit/586f5ba89cc20a81a9e2d5d0f2708e9cd1b440c0) by Vineeth K)
- **Accessibility:** `aria-hidden` support for `Text`, non-editable `TextInput` and `Image` ([0f39fc3000](https://github.com/facebook/react-native/commit/0f39fc3000411a43711814e0ab9cca1f7093b625) by [@mdjastrzebski](https://github.com/mdjastrzebski))
- **Build:** Fixed babel plugin validation error when coverage instrumentation is enabled ([191ddc1ec7](https://github.com/facebook/react-native/commit/191ddc1ec72be6641ebb8b9cb729cf0e142fff55) by Umar Mohammad)
- **Casting:** Casting rawValue to int was incorrectly truncating ([31b9f10364](https://github.com/facebook/react-native/commit/31b9f103645e67586bdfc5c2f590c28c04ca3871) by [@javache](https://github.com/javache))
- **Codegen:** Help Codegen find library's package.json if some libraries using `exports` field in their package.json file and the `./package.json` subpath is not explicitly defined ([739dfd2141](https://github.com/facebook/react-native/commit/739dfd2141015a8126448bda64a559f5bf22672e) by [@RakaDoank](https://github.com/RakaDoank))
- **Hermes:** Change leftover references to `hermes.framework` to `hermesvm.framework` ([7f051c5470](https://github.com/facebook/react-native/commit/7f051c54701b3585f76f63846abbf7e68e2688d2) by [@j-piasecki](https://github.com/j-piasecki))
- **Hermes V1:** Fixed coordinates for Hermes V1 artifacts ([674fb77d93](https://github.com/facebook/react-native/commit/674fb77d93dfe67a5fe90449dc71b195b1851e13) by [@j-piasecki](https://github.com/j-piasecki))
- **Performance Panel:** Fix typo in Performance.js type checking condition ([6caf2dfa38](https://github.com/facebook/react-native/commit/6caf2dfa382fd4f1184b8d21b030c36687a256e4) by [@YangJonghun](https://github.com/YangJonghun))
- **Performance Panel:** Add default cases to switch statements in headers ([323fe3a5d4](https://github.com/facebook/react-native/commit/323fe3a5d471ae5a2f94d5c2bd13cc97feffe0a5) by [@NSProgrammer](https://github.com/NSProgrammer))
- **ReactCommon:** Bring back ContextContainer::Shared = std::shared_ptr<const ContextContainer> alias ([daeb6e99ab](https://github.com/facebook/react-native/commit/daeb6e99abbca2b6395a9a703d2b0bb9e5091fb7) by [@christophpurrer](https://github.com/christophpurrer))
- **ReactCommon:** Bring back SharedImageManager = std::shared_ptr<ImageManager> alias ([4718b35259](https://github.com/facebook/react-native/commit/4718b35259135b3503033a0061ae84e15d4eb450) by [@christophpurrer](https://github.com/christophpurrer))
- **ReactCommon:** Fixed Type Conversion Error in DynamicEventPayload ([ff38d59cff](https://github.com/facebook/react-native/commit/ff38d59cff92e0a50f0dd70384fbc4dd11d969c4) by Harini Malothu)
- **ReactCommon:** Fixed Type Conversion Error in CSSHexColor ([2ca88a0069](https://github.com/facebook/react-native/commit/2ca88a0069969bf115da6f0ea9f2fbbae9c9226c) by [@anupriya13](https://github.com/anupriya13))
- **TestCallInvoker:** Fix memory leak in TestCallInvoker ([9f2fbc23e4](https://github.com/facebook/react-native/commit/9f2fbc23e48af9be56b3729d514fbb3fff4ba376) by [@christophpurrer](https://github.com/christophpurrer))
#### Android specific
- **Accessability:** Stabilize custom accessibility action IDs to prevent "incompatible action" errors in TalkBack. ([626568f9a3](https://github.com/facebook/react-native/commit/626568f9a3f956a52f6c55df1dc3bc5cd017e353) by [@leg234-png](https://github.com/leg234-png))
- **Build From Source:** Fix build from source due to missing folder error on Gradle 9.0 ([9fbce3eff1](https://github.com/facebook/react-native/commit/9fbce3eff18060f16e796badc415ba733ede19af) by [@cortinico](https://github.com/cortinico))
- **Determinism:** Turned off build IDs for native libraries, fixing issues with reproducibility ([4b8dbe7642](https://github.com/facebook/react-native/commit/4b8dbe7642be53d0ccfc68ca8c9b3f5e750a68c0) by [@Rexogamer](https://github.com/Rexogamer))
- **DevTools:** Fix stack trace linkifying failing when using Android emulator and other situations where the device and debugger have different bundle urls ([794df48ad6](https://github.com/facebook/react-native/commit/794df48ad6a259022e66de1a38ff54b5ec67c3e4) by [@vzaidman](https://github.com/vzaidman))
- **Edge to Edge:** Fix `Dimensions` `window` values on Android < 15 when edge-to-edge is enabled ([3b185e4bce](https://github.com/facebook/react-native/commit/3b185e4bcef24e0689cccd4cf250d469b114d4da) by [@zoontek](https://github.com/zoontek))
- **Fonts:** Update font scale when recreating `RootView` ([5cda3065ce](https://github.com/facebook/react-native/commit/5cda3065ce635460a7458cbab5c10e24bea3bfe2) by [@j-piasecki](https://github.com/j-piasecki))
- **Fonts:** Fix incorrect positioning of inline view at the end of string when RTL text in LTR container ([7f224941bb](https://github.com/facebook/react-native/commit/7f224941bb807919b487d8e1634dd2124f9258b8) by [@NickGerleman](https://github.com/NickGerleman))
- **Hermes V1:** Changed the coordinates of hermes artifacts when using Hermes V1 ([d0fb33822d](https://github.com/facebook/react-native/commit/d0fb33822de38183895c8b3421f46966909beaf3) by [@j-piasecki](https://github.com/j-piasecki))
- **Locale:** Use the first available locale instead of the default one to decide `isDevicePreferredLanguageRTL` ([a03780d279](https://github.com/facebook/react-native/commit/a03780d279d0944e0dcbbf5a93680775006598b0) by Kaining Zhong)
- **New Architecture:** Correctly account for insets on first render of Modals on New Arch ([2e76fc8e8e](https://github.com/facebook/react-native/commit/2e76fc8e8ea01fbce5bd131f675364e688f49088) by [@cortinico](https://github.com/cortinico))
- **Performance:** Fix mounting is very slow on Android by shipping native transform optimizations ([c557311ed8](https://github.com/facebook/react-native/commit/c557311ed836cded8548c5bca32f3eded0abc7ff) by [@cortinico](https://github.com/cortinico))
- **Scroll:** Fixed an issue where shadow tree and native tree layouts mismatch at the end of a scroll event ([1828c53f85](https://github.com/facebook/react-native/commit/1828c53f85faf599a485b3859f8b62586696265f) by [@Abbondanzo](https://github.com/Abbondanzo))
- **Start up:** Fix wrong default for `jsBundleAssetPath` on `DefaultReactHost` ([2246e2b82c](https://github.com/facebook/react-native/commit/2246e2b82cf0c433f9a9b385ea98e532c6f322c6) by [@cortinico](https://github.com/cortinico))
#### iOS specific
- **Build:** Fixed using USE_FRAMEWORKS (static/dynamic) with precompiled binaries ([e723ca4d6b](https://github.com/facebook/react-native/commit/e723ca4d6b86d5a98449498395c700513ceba555) by [@chrfalch](https://github.com/chrfalch))
- **Build:** Non-UTF8 crashes Info.plist local frameworks ([91e69b5d4c](https://github.com/facebook/react-native/commit/91e69b5d4c768278680a8d9ae979bc267624ce98) by [@philipheinser](https://github.com/philipheinser))
- **Build:** Fixed variable naming error in `set_fast_float_config` method in `react_native_pods.rb` ([327057fad5](https://github.com/facebook/react-native/commit/327057fad5c78a95e6c039bfe380d78672e83a43) by [@eliotfallon213](https://github.com/eliotfallon213))
- **Build:** Fix pure cocoapods dynamic framework build ([aa4555eaf1](https://github.com/facebook/react-native/commit/aa4555eaf1b6aab83660c600e867fa6c2da4128e) by [@cipolleschi](https://github.com/cipolleschi))
- **Codegen:** Fix regression that skips artifacts code generation ([f6f5ea0b2e](https://github.com/facebook/react-native/commit/f6f5ea0b2eed894725d8f6e8bd045c99c3182026) by [@kitten](https://github.com/kitten))
- **Native Modules:** Fix concurrent calls into resolve/reject inside native modules ([dc879950d1](https://github.com/facebook/react-native/commit/dc879950d196dfd429229f1c4c8e743ef1799d11) by [@RSNara](https://github.com/RSNara))
- **New Architecture:** Fix overriding (xc)framework Info.plist files with RCTNewArchEnabled field ([f84514a88b](https://github.com/facebook/react-native/commit/f84514a88be00f8dcae7972f84aa89d829392a58) by [@msynowski](https://github.com/msynowski))
- **Prebuild:** Fix Node scripts related to prebuilt tarball extraction for paths containing whitespaces ([9731e8ebc5](https://github.com/facebook/react-native/commit/9731e8ebc5ea87526a91b9903172639e062cd920) by [@kitten](https://github.com/kitten))
- **Prebuild:** Use autolinking-generated react-native-config output in second step of cocoapods linking that generates artifacts and generated source ([f170db412b](https://github.com/facebook/react-native/commit/f170db412b3ab46fd0894d5d66431d9c230cd3a8) by [@kitten](https://github.com/kitten))
- **RCTAlertController:** Simplify RCTAlertController, don't create additional UIWindow ([05c4321b19](https://github.com/facebook/react-native/commit/05c4321b194c3d0e146b6085bcaccc75acd3fd67) by [@okwasniewski](https://github.com/okwasniewski))
- **RCTPullToRefreshViewComponentView:** Properly initialize the `RCTPullToRefreshViewComponentView` ([27217e8bd6](https://github.com/facebook/react-native/commit/27217e8bd601757b5db6efc022db428b552a2aa4) by [@cipolleschi](https://github.com/cipolleschi))
- **RCTReactNativeFactory:** Ask the delegate for `getModuleForClass` and `getModuleInstanceFromClass` ([85b47afb48](https://github.com/facebook/react-native/commit/85b47afb48e50b036d2c2c79a008f571d3bfcb43) by [@cipolleschi](https://github.com/cipolleschi))
- **ScrollView:** Correctly propagate `ScrollView` props to `RefreshControl` ([09daad27ea](https://github.com/facebook/react-native/commit/09daad27ea22b83fab65176ea3c7f5f1488ba408) by [@cipolleschi](https://github.com/cipolleschi))
- **ScrollView:** Make sure that `ScrollView` recycled refresh control have the right props setup. ([21b93d8d7d](https://github.com/facebook/react-native/commit/21b93d8d7d46a26f728df19764f85a8aebf318bb) by [@cipolleschi](https://github.com/cipolleschi))
- **Switch:** Fixed a crash when rendering the `Switch` component ([28275a0f7b](https://github.com/facebook/react-native/commit/28275a0f7b182a215010d47fb841d9c2c36bb24c) by [@cipolleschi](https://github.com/cipolleschi))
- **Switch:** Fix Switch layout to work with iOS26 ([91d427fe52](https://github.com/facebook/react-native/commit/91d427fe52a307f9aa8579912ef956d61808dad2) by [@cipolleschi](https://github.com/cipolleschi))
- **Text:** Fix selectable prop not working correctly ([f004cd39bc](https://github.com/facebook/react-native/commit/f004cd39bc4b632006085cbcf61df52bc5d25242) by [@iamAbhi-916](https://github.com/iamAbhi-916))
- **TextInput:** Update TextInput recycling logic to clean up the `inputAccessoryView` dependency. ([eb08f54594](https://github.com/facebook/react-native/commit/eb08f545948de9e2eca91ab3cb7569670c553b15) by [@ArturKalach](https://github.com/ArturKalach))
- **TextInput:** Fixed TextInput behavior when `maxLength={null}` is passed ([56ad53cb14](https://github.com/facebook/react-native/commit/56ad53cb14b5c842714fcf976b6ba81f68c140f2) by [@cipolleschi](https://github.com/cipolleschi))
- **View:** Inline `View` alignment with `lineHeight` in Text ([6da351a5ed](https://github.com/facebook/react-native/commit/6da351a5ed80a10138a5558afcb380410c8a93c9) by [@intergalacticspacehighway](https://github.com/intergalacticspacehighway))
### Security
- **Network:** Fixed vulnerability on undici and on-headers ([dd00c9055a](https://github.com/facebook/react-native/commit/dd00c9055a8f0c9ceac1716385a8a9874f7a4c2e) by [@cipolleschi](https://github.com/cipolleschi))
## v0.81.4
### Fixed
#### iOS specific
- Fix regression that skips artifacts code generation ([f6f5ea0b2e](https://github.com/facebook/react-native/commit/f6f5ea0b2eed894725d8f6e8bd045c99c3182026) by [@kitten](https://github.com/kitten))
- Reapplied "Use autolinking-generated react-native-config output in second step of cocoapods linking that generates artifacts and generated source" ([bb73315a3f](https://github.com/facebook/react-native/commit/bb73315a3fd8cd203c4ddb3ffa10bfec307c7e92) by [@kitten](https://github.com/kitten))
## v0.81.3
### Fixed
#### iOS specific
- Reverted "Use autolinking-generated react-native-config output in second step of cocoapods linking that generates artifacts and generated source" ([537e3ad930](https://github.com/facebook/react-native/commit/537e3ad93041c0cef959f0d20586fe97818900a6) by [@gabrieldonadel](https://github.com/gabrieldonadel))
## v0.81.2
### Added
#### Android specific
- Create a debugOptimized buildType for Android ([5e3edafec6](https://github.com/facebook/react-native/commit/5e3edafec6c69558521061dced7a6bcd046576b0) by [@cortinico](https://github.com/cortinico))
- Add `useNativeEqualsInNativeReadableArrayAndroid` and `useNativeTransformHelperAndroid` feature flag to the experimental channel. This should alleviate some of the perf issue users are seeing on Android + Reanimated + NewArch on 0.81([a346096da8](https://github.com/facebook/react-native/commit/a346096da81fccf5fbc82d83bfc128695e6ec3a5) by [@cortinico](https://github.com/cortinico))
### Fixed
#### iOS specific
- Fix Node scripts related to prebuilt tarball extraction for paths containing whitespaces ([366f2ad505](https://github.com/facebook/react-native/commit/366f2ad5057ffecc1f5b211f6aae29567ae6b7e5) by [@kitten](https://github.com/kitten))
- Use autolinking-generated react-native-config output in second step of cocoapods linking that generates artifacts and generated source ([a2eb29e5e7](https://github.com/facebook/react-native/commit/a2eb29e5e7aef8bbdf4c647c8467b5292b013b20) by [@kitten](https://github.com/kitten))
## v0.81.1
### Added
@@ -257,6 +14,7 @@
- **Infra:** Add missing Babel dependencies ([bf2c3af93b](https://github.com/facebook/react-native/commit/bf2c3af93b146943cb35866fa9badcd188e63f5b) by [@tido64](https://github.com/tido64))
- **Accessibility:** fix `aria-label` on `TextInput` ([6965d57e75](https://github.com/facebook/react-native/commit/6965d57e75ed0cf9f265c6020d478ddb9af4bf10) by [@mdjastrzebski](https://github.com/mdjastrzebski))
#### iOS specific
- **TextInput:** Setting maxLength to 0 in TextInput now correctly blocks typing ([c5956da8c0](https://github.com/facebook/react-native/commit/c5956da8c0b735d47761af51019ed25b49001c00) by [@riteshshukla04](https://github.com/riteshshukla04))
@@ -270,6 +28,7 @@
- **Prebuild:** Fix "file exists" error in `ReactNativeDependencies.podspec` ([4c570b5d31](https://github.com/facebook/react-native/commit/4c570b5d31ef46e04e5fa26fa92d7f7090bf15e2) by [@vonovak](https://github.com/vonovak))
- **Prebuild:** added explicit handling of ReactCodegen ([6526a98d68](https://github.com/facebook/react-native/commit/6526a98d68dbc8578ea15cbf117c0a216c6e9af0) by [@cipolleschi](https://github.com/cipolleschi))
## v0.81.0
### Breaking
@@ -824,10 +583,6 @@
- **Text:** Selection range not respected when changing text or selection when selection is forced ([d32ea66e6a](https://github.com/facebook/react-native/commit/d32ea66e6a945dd84092532401b265b12d482668) by Olivier Bouillet)
- **TextInput:** Fix TextInput `onContentSizeChange` event being dispatched only once on iOS on the new architecture ([5fd5188172](https://github.com/facebook/react-native/commit/5fd51881727b2d86f87abf04db032940ac0ec8c4) by [@j-piasecki](https://github.com/j-piasecki))
## v0.79.7
See [CHANGELOG-0.7x](./CHANGELOG-0.7x.md#v0797)
## v0.79.6
See [CHANGELOG-0.7x](./CHANGELOG-0.7x.md#v0796)
+2 -5
View File
@@ -17,13 +17,10 @@
<img src="https://img.shields.io/npm/v/react-native?color=brightgreen&label=npm%20package" alt="Current npm package version." />
</a>
<a href="https://reactnative.dev/docs/contributing">
<img src="https://img.shields.io/badge/PRs-welcome-brightgreen.svg" alt="PRs are welcome!" />
<img src="https://img.shields.io/badge/PRs-welcome-brightgreen.svg" alt="PRs welcome!" />
</a>
<a href="https://twitter.com/intent/follow?screen_name=reactnative">
<img src="https://img.shields.io/twitter/follow/reactnative.svg?label=Follow%20@reactnative" alt="Follow @reactnative on X" />
</a>
<a href="https://bsky.app/profile/reactnative.dev">
<img src="https://img.shields.io/badge/Bluesky-0285FF?logo=bluesky&logoColor=fff" alt="Follow @reactnative.dev on Bluesky" />
<img src="https://img.shields.io/twitter/follow/reactnative.svg?label=Follow%20@reactnative" alt="Follow @reactnative" />
</a>
</p>
+7 -2
View File
@@ -104,6 +104,10 @@ tasks.register("build") {
tasks.register("publishAllToMavenTempLocal") {
description = "Publish all the artifacts to be available inside a Maven Local repository on /tmp."
dependsOn(":packages:react-native:ReactAndroid:publishAllPublicationsToMavenTempLocalRepository")
// We don't publish the external-artifacts to Maven Local as ci is using it via workspace.
dependsOn(
":packages:react-native:ReactAndroid:hermes-engine:publishAllPublicationsToMavenTempLocalRepository"
)
}
tasks.register("publishAndroidToSonatype") {
@@ -124,14 +128,15 @@ if (project.findProperty("react.internal.useHermesNightly")?.toString()?.toBoole
That's fine for local development, but you should not commit this change.
********************************************************************************
"""
"""
.trimIndent()
)
allprojects {
configurations.all {
resolutionStrategy.dependencySubstitution {
substitute(project(":packages:react-native:ReactAndroid:hermes-engine"))
.using(module("com.facebook.hermes:hermes-android:0.+"))
// TODO: T237406039 update coordinates
.using(module("com.facebook.react:hermes-android:0.+"))
.because("Users opted to use hermes from nightly")
}
}
+16 -19
View File
@@ -3057,30 +3057,30 @@ type util$InspectOptions = {
};
declare type util$ParseArgsOption =
| $ReadOnly<{|
| {|
type: 'boolean',
multiple?: false,
short?: string,
default?: boolean,
|}>
| $ReadOnly<{|
|}
| {|
type: 'boolean',
multiple: true,
short?: string,
default?: Array<boolean>,
|}>
| $ReadOnly<{|
|}
| {|
type: 'string',
multiple?: false,
short?: string,
default?: string,
|}>
| $ReadOnly<{|
|}
| {|
type: 'string',
multiple: true,
short?: string,
default?: Array<string>,
|}>;
|};
type util$ParseArgsOptionToValue<TOption> = TOption['type'] extends 'boolean'
? TOption['multiple'] extends true
@@ -3137,7 +3137,7 @@ declare module 'util' {
declare function stripVTControlCharacters(str: string): string;
declare function parseArgs<
TOptions: {+[string]: util$ParseArgsOption} = {||},
TOptions: {[string]: util$ParseArgsOption} = {||},
>(config: {|
args?: Array<string>,
options?: TOptions,
@@ -3995,16 +3995,13 @@ declare class Process extends events$EventEmitter {
initgroups?: (user: number | string, extra_group: number | string) => void;
kill(pid: number, signal?: string | number): void;
mainModule: Object;
memoryUsage: {
(): {
arrayBuffers: number,
rss: number,
heapTotal: number,
heapUsed: number,
external: number,
...
},
rss: () => number,
memoryUsage(): {
arrayBuffers: number,
rss: number,
heapTotal: number,
heapUsed: number,
external: number,
...
};
nextTick: <T>(cb: (...T) => mixed, ...T) => void;
pid: number;
-7
View File
@@ -4,13 +4,6 @@ org.gradle.caching=true
android.useAndroidX=true
# Those 2 properties are needed to make our project compatible with
# AGP 9.0.0 for the time being. Ideally we should not opt-out of
# builtInKotlin and newDsl once AGP 9.0.0 hits stable.
# More on this: https://developer.android.com/build/releases/agp-preview#android-gradle-plugin-built-in-kotlin
android.builtInKotlin=false
android.newDsl=false
# Use this property to specify which architecture you want to build.
# You can also override it from the CLI using
# ./gradlew <task> -PreactNativeArchitectures=x86_64
+12 -11
View File
@@ -58,8 +58,8 @@
"@jest/create-cache-key-function": "^29.7.0",
"@microsoft/api-extractor": "^7.52.2",
"@octokit/rest": "^22.0.0",
"@react-native/metro-babel-transformer": "0.83.0-main",
"@react-native/metro-config": "0.83.0-main",
"@react-native/metro-babel-transformer": "0.82.0",
"@react-native/metro-config": "0.82.0",
"@tsconfig/node22": "22.0.2",
"@types/react": "^19.1.0",
"@typescript-eslint/parser": "^8.36.0",
@@ -86,7 +86,7 @@
"eslint-plugin-relay": "^1.8.3",
"fb-dotslash": "0.5.8",
"flow-api-translator": "0.32.0",
"flow-bin": "^0.289.0",
"flow-bin": "^0.280.0",
"glob": "^7.1.1",
"hermes-eslint": "0.32.0",
"hermes-transform": "0.32.0",
@@ -100,27 +100,28 @@
"jsonc-parser": "2.2.1",
"markdownlint-cli2": "^0.17.2",
"markdownlint-rule-relative-links": "^3.0.0",
"memfs": "^4.38.2",
"metro-babel-register": "^0.83.3",
"metro-transform-plugins": "^0.83.3",
"memfs": "^4.7.7",
"metro-babel-register": "^0.83.1",
"metro-transform-plugins": "^0.83.1",
"micromatch": "^4.0.4",
"node-fetch": "^2.2.0",
"nullthrows": "^1.1.1",
"prettier": "3.6.2",
"prettier-plugin-hermes-parser": "0.32.0",
"react": "19.2.0",
"react-test-renderer": "19.2.0",
"react": "19.1.1",
"react-test-renderer": "19.1.1",
"rimraf": "^3.0.2",
"shelljs": "^0.8.5",
"signedsource": "^2.0.0",
"signedsource": "^1.0.0",
"supports-color": "^7.1.0",
"temp-dir": "^2.0.0",
"tinybench": "^4.1.0",
"typescript": "5.8.3",
"ws": "^7.5.10"
"ws": "^6.2.3"
},
"resolutions": {
"react-is": "19.2.0",
"eslint-plugin-react-hooks": "6.1.0-canary-12bc60f5-20250613",
"react-is": "19.1.1",
"on-headers": "1.1.0",
"compression": "1.8.1"
}
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/assets-registry",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "Asset support code for React Native.",
"license": "MIT",
"repository": {
+2 -2
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/babel-plugin-codegen",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "Babel plugin to generate native module and view manager code for React Native.",
"license": "MIT",
"repository": {
@@ -26,7 +26,7 @@
],
"dependencies": {
"@babel/traverse": "^7.25.3",
"@react-native/codegen": "0.83.0-main"
"@react-native/codegen": "0.82.0"
},
"devDependencies": {
"@babel/core": "^7.25.2"
+6 -6
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/community-cli-plugin",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "Core CLI commands for React Native",
"keywords": [
"react-native",
@@ -22,16 +22,16 @@
"dist"
],
"dependencies": {
"@react-native/dev-middleware": "0.83.0-main",
"@react-native/dev-middleware": "0.82.0",
"debug": "^4.4.0",
"invariant": "^2.2.4",
"metro": "^0.83.3",
"metro-config": "^0.83.3",
"metro-core": "^0.83.3",
"metro": "^0.83.1",
"metro-config": "^0.83.1",
"metro-core": "^0.83.1",
"semver": "^7.1.3"
},
"devDependencies": {
"metro-resolver": "^0.83.3"
"metro-resolver": "^0.83.1"
},
"peerDependencies": {
"@react-native-community/cli": "*",
@@ -119,6 +119,7 @@ async function runServer(
watchFolders,
});
const {middleware, websocketEndpoints} = createDevMiddleware({
projectRoot,
serverBaseUrl: devServerUrl,
logger: createDevMiddlewareLogger(terminalReporter),
});
@@ -88,6 +88,7 @@ Diff: ${styleText(['dim', 'underline'], newVersion?.diffUrl ?? 'none')}
}
}
// $FlowFixMe
function isDiffPurgeEntry(data: Partial<DiffPurge>): data is DiffPurge {
return (
// $FlowFixMe[incompatible-type-guard]
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/core-cli-utils",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "React Native CLI library for Frameworks to build on",
"license": "MIT",
"main": "./src/index.flow.js",
+2 -2
View File
@@ -1,5 +1,5 @@
@generated SignedSource<<4bb67766e15e25a481c4c38873260a7a>>
Git revision: 7aa57d13e50ce9d74a91c9315c9b0ded00fbc19f
@generated SignedSource<<b6a779e724ecce5e727ee674dc20f809>>
Git revision: e87564a24cf233c60aaebee8c418ec85724f7214
Built with --nohooks: false
Is local checkout: false
Remote URL: https://github.com/facebook/react-native-devtools-frontend
Binary file not shown.

Before

Width:  |  Height:  |  Size: 45 KiB

After

Width:  |  Height:  |  Size: 53 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 51 KiB

After

Width:  |  Height:  |  Size: 66 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.0 KiB

After

Width:  |  Height:  |  Size: 7.1 KiB

File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -1 +1 @@
import*as e from"../root/root.js";const t=e.Runtime.RNExperimentName,i={didInitializeExperiments:!1,isReactNativeEntryPoint:!1};class n{name;title;unstable;docLink;feedbackLink;enabledByDefault;constructor(e){this.name=e.name,this.title=e.title,this.unstable=e.unstable,this.docLink=e.docLink,this.feedbackLink=e.feedbackLink,this.enabledByDefault=function(e,t){if(null==e)return()=>t;if("boolean"==typeof e)return()=>e;return e}(e.enabledByDefault,!1)}}const r=new class{#e=new Map;#t=new Set;register(e){if(i.didInitializeExperiments)throw new Error("Experiments must be registered before constructing MainImpl");const{name:t}=e;if(this.#e.has(t))throw new Error(`React Native Experiment ${t} is already registered`);this.#e.set(t,new n(e))}enableExperimentsByDefault(e){if(i.didInitializeExperiments)throw new Error("Experiments must be configured before constructing MainImpl");for(const i of e)if(Object.prototype.hasOwnProperty.call(t,i)){const e=this.#e.get(i);if(!e)throw new Error(`React Native Experiment ${i} is not registered`);e.enabledByDefault=()=>!0}else this.#t.add(i)}copyInto(e,t=""){for(const[n,r]of this.#e)e.register(n,t+r.title,r.unstable,r.docLink,r.feedbackLink),r.enabledByDefault({isReactNativeEntryPoint:i.isReactNativeEntryPoint})&&e.enableExperimentsByDefault([n]);for(const t of this.#t)e.enableExperimentsByDefault([t]);i.didInitializeExperiments=!0}};r.register({name:t.JS_HEAP_PROFILER_ENABLE,title:"Enable Heap Profiler (Memory Panel)",unstable:!1,enabledByDefault:({isReactNativeEntryPoint:e})=>!e}),r.register({name:t.REACT_NATIVE_SPECIFIC_UI,title:"Show React Native-specific UI",unstable:!1,enabledByDefault:({isReactNativeEntryPoint:e})=>e}),r.register({name:t.ENABLE_NETWORK_PANEL,title:"Enable Network panel",unstable:!0,enabledByDefault:()=>!1});var a=Object.freeze({__proto__:null,Instance:r,RNExperimentName:t,setIsReactNativeEntryPoint:function(e){if(i.didInitializeExperiments)throw new Error("setIsReactNativeEntryPoint must be called before constructing MainImpl");i.isReactNativeEntryPoint=e}});export{a as RNExperimentsImpl};
import*as e from"../root/root.js";const t=e.Runtime.RNExperimentName,n={didInitializeExperiments:!1,isReactNativeEntryPoint:!1};class i{name;title;unstable;docLink;feedbackLink;enabledByDefault;constructor(e){this.name=e.name,this.title=e.title,this.unstable=e.unstable,this.docLink=e.docLink,this.feedbackLink=e.feedbackLink,this.enabledByDefault=function(e,t){if(null==e)return()=>t;if("boolean"==typeof e)return()=>e;return e}(e.enabledByDefault,!1)}}const r=new class{#e=new Map;#t=new Set;register(e){if(n.didInitializeExperiments)throw new Error("Experiments must be registered before constructing MainImpl");const{name:t}=e;if(this.#e.has(t))throw new Error(`React Native Experiment ${t} is already registered`);this.#e.set(t,new i(e))}enableExperimentsByDefault(e){if(n.didInitializeExperiments)throw new Error("Experiments must be configured before constructing MainImpl");for(const n of e)if(Object.prototype.hasOwnProperty.call(t,n)){const e=this.#e.get(n);if(!e)throw new Error(`React Native Experiment ${n} is not registered`);e.enabledByDefault=()=>!0}else this.#t.add(n)}copyInto(e,t=""){for(const[i,r]of this.#e)e.register(i,t+r.title,r.unstable,r.docLink,r.feedbackLink),r.enabledByDefault({isReactNativeEntryPoint:n.isReactNativeEntryPoint})&&e.enableExperimentsByDefault([i]);for(const t of this.#t)e.enableExperimentsByDefault([t]);n.didInitializeExperiments=!0}};r.register({name:t.JS_HEAP_PROFILER_ENABLE,title:"Enable Heap Profiler (Memory Panel)",unstable:!1,enabledByDefault:({isReactNativeEntryPoint:e})=>!e}),r.register({name:t.REACT_NATIVE_SPECIFIC_UI,title:"Show React Native-specific UI",unstable:!1,enabledByDefault:({isReactNativeEntryPoint:e})=>e}),r.register({name:t.ENABLE_PERFORMANCE_PANEL,title:"Enable Performance panel",unstable:!0,enabledByDefault:({isReactNativeEntryPoint:e})=>!e}),r.register({name:t.ENABLE_NETWORK_PANEL,title:"Enable Network panel",unstable:!0,enabledByDefault:()=>!1});var a=Object.freeze({__proto__:null,Instance:r,RNExperimentName:t,setIsReactNativeEntryPoint:function(e){if(n.didInitializeExperiments)throw new Error("setIsReactNativeEntryPoint must be called before constructing MainImpl");n.isReactNativeEntryPoint=e}});export{a as RNExperimentsImpl};
@@ -1 +1 @@
import*as e from"../platform/platform.js";const t=new URLSearchParams(location.search);let n,r,s="";function a(){return window.location.pathname}function i(e){return["node_app","js_app"].some((t=>e.includes(t)))}class o{constructor(){}static instance(e={forceNew:null}){const{forceNew:t}=e;return n&&!t||(n=new o),n}static removeInstance(){n=void 0}static queryParam(e){return t.get(e)}static setQueryParamForTesting(e,n){t.set(e,n)}static isNode(){return void 0===r&&(r=i(a())),r}static setPlatform(e){s=e}static platform(){return s}static isDescriptorEnabled(e){const{experiment:t}=e;if("*"===t)return!0;if(t&&t.startsWith("!")&&h.isEnabled(t.substring(1)))return!1;if(t&&!t.startsWith("!")&&!h.isEnabled(t))return!1;const{condition:n}=e;return!n||n(_)}loadLegacyModule(e){console.log("Loading legacy module: "+e);return import(`../../${e}`).then((t=>(console.log("Loaded legacy module: "+e),t)))}}class l{#e=[];#t=new Set;#n=new Set;#r=new Set;#s=new Set;#a=new c;allConfigurableExperiments(){const e=[];for(const t of this.#e)this.#n.has(t.name)||e.push(t);return e}register(t,n,r,s,a){if(this.#t.has(t))throw new Error(`Duplicate registration of experiment '${t}'`);this.#t.add(t),this.#e.push(new m(this,t,n,Boolean(r),s??e.DevToolsPath.EmptyUrlString,a??e.DevToolsPath.EmptyUrlString))}isEnabled(e){return this.checkExperiment(e),!1!==this.#a.get(e)&&(!(!this.#n.has(e)&&!this.#r.has(e))||(!!this.#s.has(e)||Boolean(this.#a.get(e))))}setEnabled(e,t){this.checkExperiment(e),this.#a.set(e,t)}enableExperimentsTransiently(e){for(const t of e)this.checkExperiment(t),this.#n.add(t)}enableExperimentsByDefault(e){for(const t of e)this.checkExperiment(t),this.#r.add(t)}setServerEnabledExperiments(e){for(const t of e)this.checkExperiment(t),this.#s.add(t)}enableForTest(e){this.checkExperiment(e),this.#n.add(e)}disableForTest(e){this.checkExperiment(e),this.#n.delete(e)}clearForTest(){this.#e=[],this.#t.clear(),this.#n.clear(),this.#r.clear(),this.#s.clear()}cleanUpStaleExperiments(){this.#a.cleanUpStaleExperiments(this.#t)}checkExperiment(e){if(!this.#t.has(e))throw new Error(`Unknown experiment '${e}'`)}}class c{#e={};constructor(){try{const e=self.localStorage?.getItem("experiments");e&&(this.#e=JSON.parse(e))}catch{console.error("Failed to parse localStorage['experiments']")}}get(e){return this.#e[e]}set(e,t){this.#e[e]=t,this.#i()}cleanUpStaleExperiments(e){for(const[t]of Object.entries(this.#e))e.has(t)||delete this.#e[t];this.#i()}#i(){self.localStorage?.setItem("experiments",JSON.stringify(this.#e))}}class m{name;title;unstable;docLink;feedbackLink;#e;constructor(e,t,n,r,s,a){this.name=t,this.title=n,this.unstable=r,this.docLink=s,this.feedbackLink=a,this.#e=e}isEnabled(){return this.#e.isEnabled(this.name)}setEnabled(e){this.#e.setEnabled(this.name,e)}}const h=new l;var E,p,d,u;!function(e){e.REACT_NATIVE_SPECIFIC_UI="react-native-specific-ui",e.JS_HEAP_PROFILER_ENABLE="js-heap-profiler-enable",e.ENABLE_NETWORK_PANEL="enable-network-panel"}(E||(E={})),function(e){e.NOT_SOURCES_HIDE_ADD_FOLDER="!sources.hide_add_folder",e.REACT_NATIVE_UNSTABLE_NETWORK_PANEL="unstable_enableNetworkPanel"}(p||(p={})),function(e){e[e.ALLOW=0]="ALLOW",e[e.ALLOW_WITHOUT_LOGGING=1]="ALLOW_WITHOUT_LOGGING",e[e.DISABLE=2]="DISABLE"}(d||(d={})),function(e){e.ALL_SCRIPTS="ALL_SCRIPTS",e.SIDE_EFFECT_FREE_SCRIPTS_ONLY="SIDE_EFFECT_FREE_SCRIPTS_ONLY",e.NO_SCRIPTS="NO_SCRIPTS"}(u||(u={}));const _=Object.create(null),f={canDock:()=>Boolean(o.queryParam("can_dock")),notSourcesHideAddFolder:()=>Boolean(o.queryParam(p.NOT_SOURCES_HIDE_ADD_FOLDER)),reactNativeUnstableNetworkPanel:()=>Boolean(o.queryParam(p.REACT_NATIVE_UNSTABLE_NETWORK_PANEL))||h.isEnabled("enable-network-panel")};var x=Object.freeze({__proto__:null,get ConditionName(){return p},Experiment:m,ExperimentsSupport:l,get GenAiEnterprisePolicyValue(){return d},get HostConfigFreestylerExecutionMode(){return u},get RNExperimentName(){return E},Runtime:o,conditions:f,experiments:h,getChromeVersion:()=>{const e=navigator.userAgent.match(/(?:^|\W)(?:Chrome|HeadlessChrome)\/(\S+)/);return e&&e.length>1?e[1]:""},getPathName:a,getRemoteBase:function(e=self.location.toString()){const t=new URL(e).searchParams.get("remoteBase");if(!t)return null;const n=/\/serve_file\/(@[0-9a-zA-Z]+)\/?$/.exec(t);return n?{base:`devtools://devtools/remote/serve_file/${n[1]}/`,version:n[1]}:null},hostConfig:_,isNodeEntry:i});export{x as Runtime};
import*as e from"../platform/platform.js";const t=new URLSearchParams(location.search);let n,r,s="";function a(){return window.location.pathname}function i(e){return["node_app","js_app"].some((t=>e.includes(t)))}class o{constructor(){}static instance(e={forceNew:null}){const{forceNew:t}=e;return n&&!t||(n=new o),n}static removeInstance(){n=void 0}static queryParam(e){return t.get(e)}static setQueryParamForTesting(e,n){t.set(e,n)}static isNode(){return void 0===r&&(r=i(a())),r}static setPlatform(e){s=e}static platform(){return s}static isDescriptorEnabled(e){const{experiment:t}=e;if("*"===t)return!0;if(t&&t.startsWith("!")&&h.isEnabled(t.substring(1)))return!1;if(t&&!t.startsWith("!")&&!h.isEnabled(t))return!1;const{condition:n}=e;return!n||n(_)}loadLegacyModule(e){console.log("Loading legacy module: "+e);return import(`../../${e}`).then((t=>(console.log("Loaded legacy module: "+e),t)))}}class l{#e=[];#t=new Set;#n=new Set;#r=new Set;#s=new Set;#a=new c;allConfigurableExperiments(){const e=[];for(const t of this.#e)this.#n.has(t.name)||e.push(t);return e}register(t,n,r,s,a){if(this.#t.has(t))throw new Error(`Duplicate registration of experiment '${t}'`);this.#t.add(t),this.#e.push(new m(this,t,n,Boolean(r),s??e.DevToolsPath.EmptyUrlString,a??e.DevToolsPath.EmptyUrlString))}isEnabled(e){return this.checkExperiment(e),!1!==this.#a.get(e)&&(!(!this.#n.has(e)&&!this.#r.has(e))||(!!this.#s.has(e)||Boolean(this.#a.get(e))))}setEnabled(e,t){this.checkExperiment(e),this.#a.set(e,t)}enableExperimentsTransiently(e){for(const t of e)this.checkExperiment(t),this.#n.add(t)}enableExperimentsByDefault(e){for(const t of e)this.checkExperiment(t),this.#r.add(t)}setServerEnabledExperiments(e){for(const t of e)this.checkExperiment(t),this.#s.add(t)}enableForTest(e){this.checkExperiment(e),this.#n.add(e)}disableForTest(e){this.checkExperiment(e),this.#n.delete(e)}clearForTest(){this.#e=[],this.#t.clear(),this.#n.clear(),this.#r.clear(),this.#s.clear()}cleanUpStaleExperiments(){this.#a.cleanUpStaleExperiments(this.#t)}checkExperiment(e){if(!this.#t.has(e))throw new Error(`Unknown experiment '${e}'`)}}class c{#e={};constructor(){try{const e=self.localStorage?.getItem("experiments");e&&(this.#e=JSON.parse(e))}catch{console.error("Failed to parse localStorage['experiments']")}}get(e){return this.#e[e]}set(e,t){this.#e[e]=t,this.#i()}cleanUpStaleExperiments(e){for(const[t]of Object.entries(this.#e))e.has(t)||delete this.#e[t];this.#i()}#i(){self.localStorage?.setItem("experiments",JSON.stringify(this.#e))}}class m{name;title;unstable;docLink;feedbackLink;#e;constructor(e,t,n,r,s,a){this.name=t,this.title=n,this.unstable=r,this.docLink=s,this.feedbackLink=a,this.#e=e}isEnabled(){return this.#e.isEnabled(this.name)}setEnabled(e){this.#e.setEnabled(this.name,e)}}const h=new l;var E,p,d,u;!function(e){e.REACT_NATIVE_SPECIFIC_UI="react-native-specific-ui",e.JS_HEAP_PROFILER_ENABLE="js-heap-profiler-enable",e.ENABLE_PERFORMANCE_PANEL="enable-performance-panel",e.ENABLE_NETWORK_PANEL="enable-network-panel"}(E||(E={})),function(e){e.NOT_SOURCES_HIDE_ADD_FOLDER="!sources.hide_add_folder",e.REACT_NATIVE_UNSTABLE_NETWORK_PANEL="unstable_enableNetworkPanel"}(p||(p={})),function(e){e[e.ALLOW=0]="ALLOW",e[e.ALLOW_WITHOUT_LOGGING=1]="ALLOW_WITHOUT_LOGGING",e[e.DISABLE=2]="DISABLE"}(d||(d={})),function(e){e.ALL_SCRIPTS="ALL_SCRIPTS",e.SIDE_EFFECT_FREE_SCRIPTS_ONLY="SIDE_EFFECT_FREE_SCRIPTS_ONLY",e.NO_SCRIPTS="NO_SCRIPTS"}(u||(u={}));const _=Object.create(null),f={canDock:()=>Boolean(o.queryParam("can_dock")),notSourcesHideAddFolder:()=>Boolean(o.queryParam(p.NOT_SOURCES_HIDE_ADD_FOLDER)),reactNativeUnstableNetworkPanel:()=>Boolean(o.queryParam(p.REACT_NATIVE_UNSTABLE_NETWORK_PANEL))||h.isEnabled("enable-network-panel")};var x=Object.freeze({__proto__:null,get ConditionName(){return p},Experiment:m,ExperimentsSupport:l,get GenAiEnterprisePolicyValue(){return d},get HostConfigFreestylerExecutionMode(){return u},get RNExperimentName(){return E},Runtime:o,conditions:f,experiments:h,getChromeVersion:()=>{const e=navigator.userAgent.match(/(?:^|\W)(?:Chrome|HeadlessChrome)\/(\S+)/);return e&&e.length>1?e[1]:""},getPathName:a,getRemoteBase:function(e=self.location.toString()){const t=new URL(e).searchParams.get("remoteBase");if(!t)return null;const n=/\/serve_file\/(@[0-9a-zA-Z]+)\/?$/.exec(t);return n?{base:`devtools://devtools/remote/serve_file/${n[1]}/`,version:n[1]}:null},hostConfig:_,isNodeEntry:i});export{x as Runtime};
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -238,7 +238,7 @@ import"../../ui/components/icon_button/icon_button.js";import"../../ui/component
<td>${e.method}</td>
<td>${e.params?d`<code>${JSON.stringify(e.params)}</code>`:""}</td>
<td>
${e.result?d`<code>${JSON.stringify(e.result)}</code>`:e.error?d`<code>${JSON.stringify(e.error)}</code>`:"id"in e?"(pending)":""}
${e.result?d`<code>${JSON.stringify(e.result)}</code>`:e.error?d`<code>${JSON.stringify(e.error)}</code>`:"(pending)"}
</td>
<td data-value=${e.elapsedTime||0}>
${"id"in e?e.elapsedTime?U(A.sMs,{PH1:String(e.elapsedTime)}):"(pending)":""}
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -983,7 +983,7 @@ import*as e from"../../../services/trace_bounds/trace_bounds.js";import*as t fro
<p class="tooltip">${Ai(Oi.feedbackTooltip)}</p>
</div>
`,n=s.Directives.repeat([i],(()=>this.#ve),(e=>e));s.render(n,this.#e,{host:this})}}customElements.define("devtools-performance-sidebar-insights",Ui);var Bi=Object.freeze({__proto__:null,SidebarInsightsTab:Ui});class qi extends Event{removedAnnotation;static eventName="removeannotation";constructor(e){super(qi.eventName,{bubbles:!0,composed:!0}),this.removedAnnotation=e}}class Vi extends Event{annotation;static eventName="revealannotation";constructor(e){super(Vi.eventName,{bubbles:!0,composed:!0}),this.annotation=e}}class ji extends r.Widget.VBox{#ri=new r.TabbedPane.TabbedPane;#tn=new Wi;#in=new Ki;#nn=a.Settings.Settings.instance().createSetting("timeline-user-has-opened-sidebar-once",!1);userHasOpenedSidebarOnce(){return this.#nn.get()}constructor(){super(),this.setMinimumSize(170,0);const e=!S.Runtime.experiments.isEnabled("react-native-specific-ui");e&&this.#ri.appendTab("insights","Insights",this.#tn,void 0,void 0,!1,!1,0,"timeline.insights-tab"),this.#ri.appendTab("annotations","Annotations",this.#in,void 0,void 0,!1,!1,1,"timeline.annotations-tab"),this.#ri.selectTab(e?"insights":"annotations")}wasShown(){this.#nn.set(!0),this.#ri.show(this.element),this.#rn(),"insights"===this.#ri.selectedTabId&&this.#ri.tabIsDisabled("insights")&&this.#ri.selectTab("annotations")}setAnnotations(e,t){this.#in.setAnnotations(e,t),this.#rn()}#rn(){const e=this.#in.deduplicatedAnnotations();this.#ri.setBadge("annotations",e.length>0?e.length.toString():null)}setParsedTrace(e,t){this.#tn.setParsedTrace(e,t)}setInsights(e){this.#tn.setInsights(e),this.#ri.setTabEnabled("insights",null!==e)}setActiveInsight(e){this.#tn.setActiveInsight(e),e&&this.#ri.selectTab("insights")}}class Wi extends r.Widget.VBox{#sn=new Ui;constructor(){super(),this.element.classList.add("sidebar-insights"),this.element.appendChild(this.#sn)}setParsedTrace(e,t){this.#sn.parsedTrace=e,this.#sn.traceMetadata=t}setInsights(e){this.#sn.insights=e}setActiveInsight(e){this.#sn.activeInsight=e}}class Ki extends r.Widget.VBox{#sn=new xi;constructor(){super(),this.element.classList.add("sidebar-annotations"),this.element.appendChild(this.#sn)}setAnnotations(e,t){this.#sn.annotationEntryToColorMap=t,this.#sn.annotations=e}deduplicatedAnnotations(){return this.#sn.deduplicatedAnnotations()}}var Gi=Object.freeze({__proto__:null,DEFAULT_SIDEBAR_TAB:"insights",DEFAULT_SIDEBAR_WIDTH_PX:240,RemoveAnnotation:qi,RevealAnnotation:Vi,SidebarWidget:ji}),Yi={cssText:`:host{max-height:100%;overflow:hidden auto;scrollbar-width:thin}.timeline-summary{font-size:var(--sys-typescale-body4-size);flex-direction:column;padding:0 var(--sys-size-6) var(--sys-size-4) var(--sys-size-8)}.summary-range{font-weight:var(--ref-typeface-weight-medium);height:24.5px;line-height:22px}.category-summary{gap:var(--sys-size-4);display:flex;flex-direction:column}.category-row{min-height:16px;line-height:16px}.category-swatch{display:inline-block;width:var(--sys-size-6);height:var(--sys-size-6);margin-right:var(--sys-size-4);top:var(--sys-size-1);position:relative;border:var(--sys-size-1) solid var(--sys-color-neutral-outline)}.category-name{display:inline;word-break:break-all}.category-value{text-align:right;position:relative;float:right;z-index:0;width:var(--sys-size-19)}.background-bar-container{position:absolute;inset:0 0 0 var(--sys-size-3);z-index:-1}.background-bar{width:100%;float:right;height:var(--sys-size-8);background-color:var(--sys-color-surface-yellow);border-bottom:var(--sys-size-1) solid var(--sys-color-yellow-outline)}\n/*# sourceURL=${import.meta.resolve("./timelineSummary.css")} */\n`};const{render:Xi,html:Ji}=s,Zi={total:"Total",rangeSS:"Range: {PH1} {PH2}"},Qi=t.i18n.registerUIStrings("panels/timeline/components/TimelineSummary.ts",Zi),en=t.i18n.getLocalizedString.bind(void 0,Qi);class tn extends HTMLElement{#e=r.UIUtils.createShadowRootWithCoreStyles(this,{cssFile:Yi,delegatesFocus:void 0});#on=0;#an=0;#ln=0;#dn=[];set data(e){this.#ln=e.total,this.#dn=e.categories,this.#on=e.rangeStart,this.#an=e.rangeEnd,this.#i()}#i(){const e=Ji`
`,n=s.Directives.repeat([i],(()=>this.#ve),(e=>e));s.render(n,this.#e,{host:this})}}customElements.define("devtools-performance-sidebar-insights",Ui);var Bi=Object.freeze({__proto__:null,SidebarInsightsTab:Ui});class qi extends Event{removedAnnotation;static eventName="removeannotation";constructor(e){super(qi.eventName,{bubbles:!0,composed:!0}),this.removedAnnotation=e}}class Vi extends Event{annotation;static eventName="revealannotation";constructor(e){super(Vi.eventName,{bubbles:!0,composed:!0}),this.annotation=e}}class ji extends r.Widget.VBox{#ri=new r.TabbedPane.TabbedPane;#tn=new Wi;#in=new Ki;#nn=a.Settings.Settings.instance().createSetting("timeline-user-has-opened-sidebar-once",!1);userHasOpenedSidebarOnce(){return this.#nn.get()}constructor(){super(),this.setMinimumSize(170,0),this.#ri.appendTab("insights","Insights",this.#tn,void 0,void 0,!1,!1,0,"timeline.insights-tab"),this.#ri.appendTab("annotations","Annotations",this.#in,void 0,void 0,!1,!1,1,"timeline.annotations-tab"),this.#ri.selectTab("insights")}wasShown(){this.#nn.set(!0),this.#ri.show(this.element),this.#rn(),"insights"===this.#ri.selectedTabId&&this.#ri.tabIsDisabled("insights")&&this.#ri.selectTab("annotations")}setAnnotations(e,t){this.#in.setAnnotations(e,t),this.#rn()}#rn(){const e=this.#in.deduplicatedAnnotations();this.#ri.setBadge("annotations",e.length>0?e.length.toString():null)}setParsedTrace(e,t){this.#tn.setParsedTrace(e,t)}setInsights(e){this.#tn.setInsights(e),this.#ri.setTabEnabled("insights",null!==e)}setActiveInsight(e){this.#tn.setActiveInsight(e),e&&this.#ri.selectTab("insights")}}class Wi extends r.Widget.VBox{#sn=new Ui;constructor(){super(),this.element.classList.add("sidebar-insights"),this.element.appendChild(this.#sn)}setParsedTrace(e,t){this.#sn.parsedTrace=e,this.#sn.traceMetadata=t}setInsights(e){this.#sn.insights=e}setActiveInsight(e){this.#sn.activeInsight=e}}class Ki extends r.Widget.VBox{#sn=new xi;constructor(){super(),this.element.classList.add("sidebar-annotations"),this.element.appendChild(this.#sn)}setAnnotations(e,t){this.#sn.annotationEntryToColorMap=t,this.#sn.annotations=e}deduplicatedAnnotations(){return this.#sn.deduplicatedAnnotations()}}var Gi=Object.freeze({__proto__:null,DEFAULT_SIDEBAR_TAB:"insights",DEFAULT_SIDEBAR_WIDTH_PX:240,RemoveAnnotation:qi,RevealAnnotation:Vi,SidebarWidget:ji}),Yi={cssText:`:host{max-height:100%;overflow:hidden auto;scrollbar-width:thin}.timeline-summary{font-size:var(--sys-typescale-body4-size);flex-direction:column;padding:0 var(--sys-size-6) var(--sys-size-4) var(--sys-size-8)}.summary-range{font-weight:var(--ref-typeface-weight-medium);height:24.5px;line-height:22px}.category-summary{gap:var(--sys-size-4);display:flex;flex-direction:column}.category-row{min-height:16px;line-height:16px}.category-swatch{display:inline-block;width:var(--sys-size-6);height:var(--sys-size-6);margin-right:var(--sys-size-4);top:var(--sys-size-1);position:relative;border:var(--sys-size-1) solid var(--sys-color-neutral-outline)}.category-name{display:inline;word-break:break-all}.category-value{text-align:right;position:relative;float:right;z-index:0;width:var(--sys-size-19)}.background-bar-container{position:absolute;inset:0 0 0 var(--sys-size-3);z-index:-1}.background-bar{width:100%;float:right;height:var(--sys-size-8);background-color:var(--sys-color-surface-yellow);border-bottom:var(--sys-size-1) solid var(--sys-color-yellow-outline)}\n/*# sourceURL=${import.meta.resolve("./timelineSummary.css")} */\n`};const{render:Xi,html:Ji}=s,Zi={total:"Total",rangeSS:"Range: {PH1} {PH2}"},Qi=t.i18n.registerUIStrings("panels/timeline/components/TimelineSummary.ts",Zi),en=t.i18n.getLocalizedString.bind(void 0,Qi);class tn extends HTMLElement{#e=r.UIUtils.createShadowRootWithCoreStyles(this,{cssFile:Yi,delegatesFocus:void 0});#on=0;#an=0;#ln=0;#dn=[];set data(e){this.#ln=e.total,this.#dn=e.categories,this.#on=e.rangeStart,this.#an=e.rangeEnd,this.#i()}#i(){const e=Ji`
<div class="timeline-summary">
<div class="summary-range">${en(Zi.rangeSS,{PH1:t.TimeUtilities.millisToString(this.#on),PH2:t.TimeUtilities.millisToString(this.#an)})}</div>
<div class="category-summary">
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/debugger-frontend",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "Debugger frontend for React Native based on Chrome DevTools",
"keywords": [
"react-native",
@@ -1,71 +1,86 @@
#!/usr/bin/env dotslash
// @generated SignedSource<<8b06371489dc8b79c23cbf095568c91a>>
// @generated SignedSource<<02ab38b39784853e42c1e8cab3894f5b>>
{
"name": "React Native DevTools",
"platforms": {
"linux-aarch64": {
"size": 116051181,
"size": 116060647,
"hash": "sha256",
"digest": "a6060e1291f9ee7e9feecd511012c041ed2a65c6df6f8ab5aca4d96adbbc9921",
"digest": "4352f1c9848ca919101ec628bd08b87a72a828d1ab55fa43a02098329fa452fa",
"providers": [
{
"url": "https://github.com/facebook/react-native/releases/download/v0.82.0/React.Native.DevTools-linux-aarch64.tar.gz"
},
{
"type": "http",
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQOD3-UmqD25MctpnB7Ogj0A8nHDs-SgFnMNFfStIxOajFAFSN93zuoWsLD3ylc3wVuX6-L-ndcMftTd7tlR1ZZWYy4a7g78w4N1UTzIT_z9vdOXpYGe7fZrHXiBHJu0QexD0b54OcdDSEFhh0-7puUTGPnIg3pHhThiU6bf_5AqvGIEYA5FGjih3zY"
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQM24LW0nPZRk0ypuIG9prz_72YjBJNcVlGSIEpO4zdlLXgw4dFNodH7MKg9eKNTnx7wrVDDBNACrnEPt_OfXOjZyZsV9Oaqu0-vNFRdlEyis4YqmpqGLtz3LvD-9R6fzcWxJI9zrhdPvOvlXP-3Syt1UNITaxXDVqIwAAYpCaAh0oLpupAFCc2yvYw"
}
],
"format": "tar.gz",
"path": "React Native DevTools-linux-arm64/React Native DevTools"
},
"linux-x86_64": {
"size": 115927343,
"size": 115930333,
"hash": "sha256",
"digest": "354f6550617d0c6b4bb4478ad085d4efe3671ba9a1b78d90d9bfc003a523cb6d",
"digest": "11c7b07942928a6301b07fbf2bc77ce1229b2a52891f23541cdd9858b5250e64",
"providers": [
{
"url": "https://github.com/facebook/react-native/releases/download/v0.82.0/React.Native.DevTools-linux-x86_64.tar.gz"
},
{
"type": "http",
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQMVMfCfSykWSI8mB5koUEUtx819xGQGW3Tm1DBpEmjWA_g8C4PoPPDCIPpgJmB5nUKrv081_dtayoArCncyFJVs0ofbxGn0EkaEW2vW3OJ2J0XMH58v5cTLED3dT8TmWwAg6aYUTr0ch8DfVXRxsibYUIWaxJUwOJ-urR-iQm7YPQUboLElaJbM"
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQNDwm7HZRhtNxHqMr1FfSb0afHFGrn1OHxH0gOiggrLrht9QRUgJ3GG5jj7huhQzMRogE-LCMsnxh1ioOZks-YYX4KRt6Kj1-whdWsGFc7lBhPOpk1ssbYFGN1NNyuyFRmH-3nCY3lBC4AmbCUkbDTUeCi9DidCtJeyc73CZJEu7M62rIzxR2yV"
}
],
"format": "tar.gz",
"path": "React Native DevTools-linux-x64/React Native DevTools"
},
"macos-aarch64": {
"size": 110891048,
"size": 110891041,
"hash": "sha256",
"digest": "df41cfce9bc977ef4fdc66c3c892c0eedee5b07aa618550308157c51b8e75561",
"digest": "3cbe8b1b3d17e433347f1601435bb9a6cb758528a5c176a66fc52d9977223175",
"providers": [
{
"url": "https://github.com/facebook/react-native/releases/download/v0.82.0/React.Native.DevTools-macos-aarch64.tar.gz"
},
{
"type": "http",
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQOGfzOOV_mwg63orI4Hv0VQKQtE5Vk60eSl55gZDd0djjU-lmqddRZm_LxsWsek4xM7qIxqCbw6wGx7zqnrlmQGyfD98n0TBFh3uhVeYP_j3r2UkKci6tqjEqcLTHjFj3agjI6jDEe3fDpZtwKY4UMhXdVP4o1goYq13rG-IQAqIsAm04MnPFOYyp5X"
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQOmC2cqqSv4OrSJKJroYVg_NE8OE4O73AXqY7wXiYqiWQVkDt0Xnyw3ZeUpQT_Qb0-OoT5F8REKoFrB6eqwat8Ovkyina30peYTTwNUzmwnnGQEg7J0fOHNxLF4dkmU1FagXtsoWgex4dKgsK_VpcMsHj3Vp7diomkYvWBVTf_gPVEseYSN9oKq92qa"
}
],
"format": "tar.gz",
"path": "React Native DevTools.app/Contents/MacOS/React Native DevTools"
},
"macos-x86_64": {
"size": 117777930,
"size": 117766158,
"hash": "sha256",
"digest": "96805c51623a163b1d94b501e2e091f403b4c3575063bd7363f8e1550cda8dc5",
"digest": "6fb79bc2ba3008401b4c9c128248657b95b98581ccde60f8fadb622163779775",
"providers": [
{
"url": "https://github.com/facebook/react-native/releases/download/v0.82.0/React.Native.DevTools-macos-x86_64.tar.gz"
},
{
"type": "http",
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQNbF-vba13QuctGdSckSWSApEqUne0w8vGceEm5u9VNYqHzwaZu6_T0n12Ml7aHuNgAgU0OOxJKUjcr2DVsNEsjcCYwMqCjZys8yF8NfM39OH1YePjHZCw5jinydbhGxhF1zbJ_zKmuOx1FhJtzCD3CUbLSea7fuhPh6ytLUIu3Ctx4aFQLFtbJZQ"
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQMMtGn-YGdfLfTVWC8zbQkQx65Asq6iArKt1t__cjZ8UY_s6-sX5XBHr8k1SaexAO21dFZENQVZ1jW_wn_gJ9ENvosQDG1KfWMViKsHli0xRzZ1HVsgPIj_KVXe907QZwwtJf2XhgH0HT8dfH-AQdDcd0_TB5DFUwOsHzhH0nBrHet7YFkbJtPTaA"
}
],
"format": "tar.gz",
"path": "React Native DevTools.app/Contents/MacOS/React Native DevTools"
},
"windows-x86_64": {
"size": 125533589,
"size": 125527537,
"hash": "sha256",
"digest": "7f560e6d68b4b917c53ba0518a778a20e267cce55474ad972d345b2738746a52",
"digest": "579a5b0944c51c3b1b541ad5af66c1ffedf93cae2a891ecdf88cb7219fd9b096",
"providers": [
{
"url": "https://github.com/facebook/react-native/releases/download/v0.82.0/React.Native.DevTools-windows-x86_64.tar.gz"
},
{
"type": "http",
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQPZzccNNBkp1OKt_SPZ-iDoK5LDWyvZhFMgz4oTf9Ja9PlKU7i_5ydAVd714waJteCM1cdAidPN6PumBRs1uK12E9moytEskWXlMPbQObFpaTnkxLn6xp3N5EAKbAXvPfecX41Tz_7HRqh19_hW3XpwXF-VNsAdtn59ApMtX1fpN0peB1l4o57P"
"url": "https://scontent.xx.fbcdn.net/mci_ab/uap/?ab_b=m&ab_page=react_native_devtools_binaries&ab_entry=AQOQ3E8lBXqdVHbDPyVb5AOQMrDWjFrFV8fnLLBsygQvLWdpu6ixyG9PgWdwpi5jM-XcDdCHkhBdhaq-5dwT_tgRWKCAMsEBoAIUk0Xg77mGyHG2VF7bNfQ2qFBMuObrsTmrKy1nJ-UFDDm29pJD4GkFQW5NesiBwndJj8t3B8Ur8cczh_XR8rF5"
}
],
"format": "tar.gz",
+1 -2
View File
@@ -1,7 +1,6 @@
{
"name": "@react-native/debugger-shell",
"productName": "React Native DevTools",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "Experimental debugger shell for React Native for use with @react-native/debugger-frontend",
"keywords": [
"react-native",
@@ -8,15 +8,11 @@
* @format
*/
import SettingsStore from './SettingsStore.js';
// $FlowFixMe[unclear-type] We have no Flow types for the Electron API.
const {BrowserWindow, app, shell, ipcMain} = require('electron') as any;
const path = require('path');
const util = require('util');
// $FlowFixMe[unclear-type] We have no Flow types for the Electron API.
const {BrowserWindow, Menu, app, shell, ipcMain} = require('electron') as any;
const appSettings = new SettingsStore();
const windowMetadata = new WeakMap<
typeof BrowserWindow,
$ReadOnly<{
@@ -57,11 +53,10 @@ function handleLaunchArgs(argv: string[]) {
}, 1000);
}
} else {
// Create the browser window.
frontendWindow = new BrowserWindow({
...(getSavedWindowPosition(windowKey) ?? {
width: 1200,
height: 600,
}),
width: 1200,
height: 600,
webPreferences: {
partition: 'persist:react-native-devtools',
preload: require.resolve('./preload.js'),
@@ -71,8 +66,6 @@ function handleLaunchArgs(argv: string[]) {
});
// Auto-hide the Windows/Linux menu bar
frontendWindow.setMenuBarVisibility(false);
// Observe and update saved window position
setupWindowResizeListeners(frontendWindow, windowKey);
}
// Open links in the default browser instead of in new Electron windows.
@@ -98,68 +91,8 @@ function handleLaunchArgs(argv: string[]) {
frontendWindow.focus();
}
function configureAppMenu() {
const template = [
...(process.platform === 'darwin' ? [{role: 'appMenu'}] : []),
{role: 'fileMenu'},
{role: 'editMenu'},
{role: 'viewMenu'},
{role: 'windowMenu'},
{
role: 'help',
submenu: [
{
label: 'React Native Website',
click: () => shell.openExternal('https://reactnative.dev'),
},
{
label: 'Release Notes',
click: () =>
shell.openExternal(
'https://github.com/facebook/react-native/releases',
),
},
],
},
];
const menu = Menu.buildFromTemplate(template);
Menu.setApplicationMenu(menu);
}
function getSavedWindowPosition(
windowKey: string,
): ?{width: number, height: number, x?: number, y?: number} {
return appSettings.get('windowArrangements', {})[windowKey];
}
function saveWindowPosition(
windowKey: string,
position: {x: number, y: number, width: number, height: number},
) {
const windowArrangements = appSettings.get('windowArrangements', {});
windowArrangements[windowKey] = position;
appSettings.set('windowArrangements', windowArrangements);
}
function setupWindowResizeListeners(
browserWindow: typeof BrowserWindow,
windowKey: string,
) {
const savePosition = () => {
if (!browserWindow.isDestroyed()) {
const [x, y] = browserWindow.getPosition();
const [width, height] = browserWindow.getSize();
saveWindowPosition(windowKey, {x, y, width, height});
}
};
browserWindow.on('moved', savePosition);
browserWindow.on('resized', savePosition);
browserWindow.on('closed', savePosition);
}
app.whenReady().then(() => {
handleLaunchArgs(process.argv.slice(app.isPackaged ? 1 : 2));
configureAppMenu();
app.on(
'second-instance',
@@ -1,128 +0,0 @@
/**
* Copyright (c) Meta Platforms, Inc. and affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*
* @flow
* @format
* @oncall react_native
*/
// $FlowFixMe[unclear-type] We have no Flow types for the Electron API.
const {app} = require('electron') as any;
const fs = require('fs');
const path = require('path');
type Options = $ReadOnly<{
name?: string,
defaults?: Object,
}>;
/**
* A data persistence layer for storing application settings, modelled after
* [`electron-store`](https://www.npmjs.com/package/electron-store).
*
* Values are saved in a `config.json` file in `app.getPath('userData')`.
*
* Compatibility:
* - Maintains API and file format compatibility with `electron-store@8.2.0`.
* - Supports the Electron main process only.
*/
export default class SettingsStore {
#defaultValues: Object = {};
path: string;
constructor(options: Options = {}) {
options = {
name: 'config',
...options,
};
this.#defaultValues = {
...this.#defaultValues,
...options.defaults,
};
this.path = path.resolve(
app.getPath('userData'),
`${options.name ?? 'config'}.json`,
);
}
get(key: string, defaultValue?: any): any {
const store = this.store;
return store[key] !== undefined ? store[key] : defaultValue;
}
set(key: string, value: any): void {
const {store} = this;
if (typeof key === 'object') {
const object = key;
for (const [k, v] of Object.entries(object)) {
store[k] = v;
}
} else {
store[key] = value;
}
this.store = store;
}
has(key: string): boolean {
return key in this.store;
}
reset(...keys: Array<string>): void {
for (const key of keys) {
if (this.#defaultValues[key] != null) {
this.set(key, this.#defaultValues[key]);
}
}
}
delete(key: string): void {
const {store} = this;
delete store[key];
this.store = store;
}
clear(): void {
this.store = {};
for (const key of Object.keys(this.#defaultValues)) {
this.reset(key);
}
}
get store(): {[string]: mixed} {
try {
const data = fs.readFileSync(this.path, 'utf8');
const deserializedData = this._deserialize(data);
return {
...((deserializedData: any): {[string]: mixed}),
};
} catch (error) {
if (error?.code === 'ENOENT') {
this._ensureDirectory();
return {};
}
throw error;
}
}
set store(value: mixed): void {
this._ensureDirectory();
this._write(value);
}
_deserialize = (value: string): mixed => JSON.parse(value);
_serialize = (value: mixed): string =>
JSON.stringify(value, undefined, '\t') ?? '';
_ensureDirectory(): void {
fs.mkdirSync(path.dirname(this.path), {recursive: true});
}
_write(value: mixed): void {
const data = this._serialize(value);
fs.writeFileSync(this.path, data, {mode: 0o666});
}
}
@@ -16,8 +16,9 @@ const util = require('util');
// $FlowFixMe[unclear-type] We have no Flow types for the Electron API.
const {app} = require('electron') as any;
// Set the application name and version
app.setName(pkg.productName ?? pkg.name);
// Set the app name and version early - these are used in --version as well as
// in the User-Agent string.
app.setName(pkg.name);
app.setVersion(pkg.version + '-' + buildInfo.revision);
// Handle global command line arguments which don't require a window
@@ -25,14 +26,12 @@ app.setVersion(pkg.version + '-' + buildInfo.revision);
const {
values: {version = false},
} = util.parseArgs({
options: {
version: {type: 'boolean'},
},
options: {version: {type: 'boolean'}},
args: process.argv.slice(app.isPackaged ? 1 : 2),
strict: false,
});
if (version) {
console.log(`${pkg.name} v${app.getVersion()}`);
console.log(`${app.getName()} v${app.getVersion()}`);
// Not app.quit() - we want to exit immediately without initialising the graphical subsystem.
app.exit(0);
}
+5 -18
View File
@@ -30,7 +30,6 @@ async function unstable_spawnDebuggerShellWithArgs(
{
mode = 'detached',
flavor = 'prebuilt',
prebuiltBinaryPath,
}: $ReadOnly<{
// In 'syncAndExit' mode, the current process will block until the spawned process exits, and then it will exit
// with the same exit code as the spawned process.
@@ -38,13 +37,9 @@ async function unstable_spawnDebuggerShellWithArgs(
// continue to run normally.
mode?: 'syncThenExit' | 'detached',
flavor?: DebuggerShellFlavor,
prebuiltBinaryPath?: string,
}> = {},
): Promise<void> {
const [binaryPath, baseArgs] = getShellBinaryAndArgs(
flavor,
prebuiltBinaryPath,
);
const [binaryPath, baseArgs] = getShellBinaryAndArgs(flavor);
return new Promise((resolve, reject) => {
const child = spawn(binaryPath, [...baseArgs, ...args], {
@@ -114,13 +109,14 @@ export type DebuggerShellPreparationResult = $ReadOnly<{
*/
async function unstable_prepareDebuggerShell(
flavor: DebuggerShellFlavor,
{prebuiltBinaryPath}: {prebuiltBinaryPath?: string} = {},
): Promise<DebuggerShellPreparationResult> {
const [binaryPath, baseArgs] = getShellBinaryAndArgs(flavor);
try {
switch (flavor) {
case 'prebuilt':
const prebuiltResult = await prepareDebuggerShellFromDotSlashFile(
prebuiltBinaryPath ?? DEVTOOLS_BINARY_DOTSLASH_FILE,
DEVTOOLS_BINARY_DOTSLASH_FILE,
);
if (prebuiltResult.code !== 'success') {
return prebuiltResult;
@@ -132,11 +128,6 @@ async function unstable_prepareDebuggerShell(
flavor as empty;
throw new Error(`Unknown flavor: ${flavor}`);
}
const [binaryPath, baseArgs] = getShellBinaryAndArgs(
flavor,
prebuiltBinaryPath,
);
const {code, stderr} = await spawnAndGetStderr(binaryPath, [
...baseArgs,
'--version',
@@ -158,14 +149,10 @@ async function unstable_prepareDebuggerShell(
function getShellBinaryAndArgs(
flavor: DebuggerShellFlavor,
prebuiltBinaryPath: ?string,
): [string, Array<string>] {
switch (flavor) {
case 'prebuilt':
return [
require('fb-dotslash'),
[prebuiltBinaryPath ?? DEVTOOLS_BINARY_DOTSLASH_FILE],
];
return [require('fb-dotslash'), [DEVTOOLS_BINARY_DOTSLASH_FILE]];
case 'dev':
return [
// NOTE: Internally at Meta, this is aliased to a workspace that is
+5 -5
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/dev-middleware",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "Dev server middleware for React Native",
"keywords": [
"react-native",
@@ -23,8 +23,8 @@
],
"dependencies": {
"@isaacs/ttlcache": "^1.4.1",
"@react-native/debugger-frontend": "0.83.0-main",
"@react-native/debugger-shell": "0.83.0-main",
"@react-native/debugger-frontend": "0.82.0",
"@react-native/debugger-shell": "0.82.0",
"chrome-launcher": "^0.15.2",
"chromium-edge-launcher": "^0.2.0",
"connect": "^3.6.5",
@@ -33,13 +33,13 @@
"nullthrows": "^1.1.1",
"open": "^7.0.3",
"serve-static": "^1.16.2",
"ws": "^7.5.10"
"ws": "^6.2.3"
},
"engines": {
"node": ">= 20.19.4"
},
"devDependencies": {
"@react-native/debugger-shell": "0.83.0-main",
"@react-native/debugger-shell": "0.82.0",
"selfsigned": "^2.4.1",
"undici": "^5.29.0",
"wait-for-expect": "^3.0.2"
@@ -21,6 +21,10 @@ import {
withServerForEachTest,
} from './ServerUtils';
import {createHash} from 'crypto';
import fs from 'fs';
import path from 'path';
const fsPromise = fs.promises;
// WebSocket is unreliable when using fake timers.
jest.useRealTimers();
@@ -43,6 +47,7 @@ describe.each(['HTTP', 'HTTPS'])(
const serverRef = withServerForEachTest({
logger: undefined,
projectRoot: __dirname,
secure: protocol === 'HTTPS',
});
@@ -467,7 +472,14 @@ describe.each(['HTTP', 'HTTPS'])(
}
});
test('throws when attempting to pass a filesystem url', async () => {
test('reads source from disk', async () => {
// Should be just 'foo\n', but the newline can get mangled by the OS
// and/or SCM, so let's read the source of truth from disk.
const fileRealContents = await fsPromise.readFile(
path.join(__dirname, '__fixtures__', 'mock-source-file.txt'),
'utf8',
);
const {device, debugger_} = await createAndConnectTarget(
serverRef,
autoCleanup.signal,
@@ -478,7 +490,6 @@ describe.each(['HTTP', 'HTTPS'])(
vm: 'bar-vm',
},
);
try {
await sendFromTargetToDebugger(device, debugger_, 'page1', {
method: 'Debugger.scriptParsed',
@@ -489,7 +500,7 @@ describe.each(['HTTP', 'HTTPS'])(
endLine: 0,
startColumn: 0,
endColumn: 0,
hash: createHash('sha256').update('').digest('hex'),
hash: createHash('sha256').update(fileRealContents).digest('hex'),
},
});
const response = await debugger_.sendAndGetResponse({
@@ -500,15 +511,8 @@ describe.each(['HTTP', 'HTTPS'])(
},
});
expect(response.result).toEqual(
expect.objectContaining({
error: {
message: expect.stringContaining(
'Can\'t parse requested URL "__fixtures__/mock-source-file.txt"',
),
},
}),
expect.objectContaining({scriptSource: fileRealContents}),
);
// The device does not receive the getScriptSource request, since it
// is handled by the proxy.
expect(device.wrappedEventParsed).not.toBeCalledWith({
@@ -33,6 +33,7 @@ describe.each(['HTTP', 'HTTPS'])(
protocol => {
const serverRef = withServerForEachTest({
logger: undefined,
projectRoot: '',
secure: protocol === 'HTTPS',
});
const autoCleanup = withAbortSignalForEachTest();
@@ -39,6 +39,7 @@ describe('inspector proxy device message middleware', () => {
const createCustomMessageHandler = jest.fn().mockImplementation(() => null);
const {server} = await createServer({
logger: undefined,
projectRoot: '',
unstable_customInspectorMessageHandler: createCustomMessageHandler,
});
@@ -82,6 +83,7 @@ describe('inspector proxy device message middleware', () => {
const createCustomMessageHandler = jest.fn().mockImplementation(() => null);
const {server} = await createServer({
logger: undefined,
projectRoot: '',
unstable_customInspectorMessageHandler: createCustomMessageHandler,
});
const {serverBaseUrl, serverBaseWsUrl} = serverRefUrls(server);
@@ -167,6 +169,7 @@ describe('inspector proxy device message middleware', () => {
const {server} = await createServer({
logger: undefined,
projectRoot: '',
unstable_customInspectorMessageHandler: createCustomMessageHandler,
});
@@ -228,6 +231,7 @@ describe('inspector proxy device message middleware', () => {
const handleDeviceMessage = jest.fn();
const {server} = await createServer({
logger: undefined,
projectRoot: '',
unstable_customInspectorMessageHandler: () => ({
handleDeviceMessage,
handleDebuggerMessage() {},
@@ -260,6 +264,7 @@ describe('inspector proxy device message middleware', () => {
const handleDeviceMessage = jest.fn();
const {server} = await createServer({
logger: undefined,
projectRoot: '',
unstable_customInspectorMessageHandler: () => ({
handleDeviceMessage,
handleDebuggerMessage() {},
@@ -299,6 +304,7 @@ describe('inspector proxy device message middleware', () => {
const handleDebuggerMessage = jest.fn();
const {server} = await createServer({
logger: undefined,
projectRoot: '',
unstable_customInspectorMessageHandler: () => ({
handleDeviceMessage() {},
handleDebuggerMessage,
@@ -335,6 +341,7 @@ describe('inspector proxy device message middleware', () => {
const handleDebuggerMessage = jest.fn();
const {server} = await createServer({
logger: undefined,
projectRoot: '',
unstable_customInspectorMessageHandler: () => ({
handleDeviceMessage() {},
handleDebuggerMessage,
@@ -37,6 +37,7 @@ const PAGE_DEFAULTS = {
describe('inspector-proxy device socket handoff', () => {
const serverRef = withServerForEachTest({
logger: undefined,
projectRoot: '',
});
const autoCleanup = withAbortSignalForEachTest();
afterEach(() => {
@@ -27,6 +27,7 @@ jest.useFakeTimers();
describe('inspector proxy HTTP API', () => {
const serverRef = withServerForEachTest({
logger: undefined,
projectRoot: '',
});
const autoCleanup = withAbortSignalForEachTest();
afterEach(() => {
@@ -260,6 +261,7 @@ describe('inspector proxy HTTP API', () => {
describe('HTTP vs HTTPS', () => {
const secureServerRef = withServerForEachTest({
logger: undefined,
projectRoot: '',
secure: true,
});
@@ -25,6 +25,7 @@ jest.setTimeout(10000);
describe('inspector proxy React Native reloads', () => {
const serverRef = withServerForEachTest({
logger: undefined,
projectRoot: '',
});
const autoCleanup = withAbortSignalForEachTest();
afterEach(() => {
@@ -34,6 +34,7 @@ describe('enableStandaloneFuseboxShell experiment', () => {
};
const serverRef = withServerForEachTest({
logger: undefined,
projectRoot: '',
unstable_browserLauncher: BrowserLauncherWithFuseboxShell,
unstable_experiments: {
enableStandaloneFuseboxShell: true,
@@ -17,6 +17,7 @@ jest.setTimeout(10000);
describe('embedder script', () => {
const serverRef = withServerForEachTest({
logger: undefined,
projectRoot: '',
});
test('is always served', async () => {
@@ -24,6 +24,8 @@ import path from 'path';
import serveStaticMiddleware from 'serve-static';
type Options = $ReadOnly<{
projectRoot: string,
/**
* The base URL to the dev server, as reachable from the machine on which
* dev-middleware is hosted. Typically `http://localhost:${metroPort}`.
@@ -76,6 +78,7 @@ type DevMiddlewareAPI = $ReadOnly<{
}>;
export default function createDevMiddleware({
projectRoot,
serverBaseUrl,
logger,
// $FlowFixMe[incompatible-type]
@@ -93,6 +96,7 @@ export default function createDevMiddleware({
);
const inspectorProxy = new InspectorProxy(
projectRoot,
serverBaseUrl,
eventReporter,
experiments,
+2 -2
View File
@@ -8,6 +8,8 @@
* @format
*/
export {default as createDevMiddleware} from './createDevMiddleware';
export type {
BrowserLauncher,
DebuggerShellPreparationResult,
@@ -18,7 +20,5 @@ export type {
CustomMessageHandlerConnection,
CreateCustomMessageHandlerFn,
} from './inspector-proxy/CustomMessageHandler';
export type {Logger} from './types/Logger';
export {default as unstable_DefaultBrowserLauncher} from './utils/DefaultBrowserLauncher';
export {default as createDevMiddleware} from './createDevMiddleware';
@@ -28,7 +28,9 @@ import type {
import CdpDebugLogging from './CdpDebugLogging';
import DeviceEventReporter from './DeviceEventReporter';
import * as fs from 'fs';
import invariant from 'invariant';
import * as path from 'path';
import WS from 'ws';
const debug = require('debug')('Metro:InspectorProxy');
@@ -73,6 +75,7 @@ export type DeviceOptions = $ReadOnly<{
name: string,
app: string,
socket: WS,
projectRoot: string,
eventReporter: ?EventReporter,
createMessageMiddleware: ?CreateCustomMessageHandlerFn,
deviceRelativeBaseUrl: URL,
@@ -117,6 +120,9 @@ export default class Device {
// Mapping built from scriptParsed events and used to fetch file content in `Debugger.getScriptSource`.
#scriptIdToSourcePathMapping: Map<string, string> = new Map();
// Root of the project used for relative to absolute source path conversion.
#projectRoot: string;
#deviceEventReporter: ?DeviceEventReporter;
#pagesPollingIntervalId: ReturnType<typeof setInterval>;
@@ -145,6 +151,7 @@ export default class Device {
name,
app,
socket,
projectRoot,
eventReporter,
createMessageMiddleware,
serverRelativeBaseUrl,
@@ -156,6 +163,7 @@ export default class Device {
this.#name = name;
this.#app = app;
this.#deviceSocket = socket;
this.#projectRoot = projectRoot;
this.#serverRelativeBaseUrl = serverRelativeBaseUrl;
this.#deviceRelativeBaseUrl = deviceRelativeBaseUrl;
this.#deviceEventReporter = eventReporter
@@ -872,7 +880,7 @@ export default class Device {
return this.#processDebuggerSetBreakpointByUrl(req, debuggerInfo);
case 'Debugger.getScriptSource':
// Sends response to debugger via side-effect
void this.#processDebuggerGetScriptSource(req, socket);
this.#processDebuggerGetScriptSource(req, socket);
return null;
case 'Network.loadNetworkResource':
// If we're rewriting URLs (to frontend-relative), we don't want to
@@ -957,10 +965,10 @@ export default class Device {
return processedReq;
}
async #processDebuggerGetScriptSource(
#processDebuggerGetScriptSource(
req: CDPRequest<'Debugger.getScriptSource'>,
socket: WS,
): Promise<void> {
): void {
const sendSuccessResponse = (scriptSource: string) => {
const result: {
scriptSource: string,
@@ -997,23 +1005,33 @@ export default class Device {
const pathToSource = this.#scriptIdToSourcePathMapping.get(
req.params.scriptId,
);
try {
const httpURL =
pathToSource == null ? null : this.#tryParseHTTPURL(pathToSource);
if (!httpURL) {
throw new Error(
`Can't parse requested URL ${pathToSource === undefined ? 'undefined' : JSON.stringify(pathToSource)}`,
if (pathToSource != null) {
const httpURL = this.#tryParseHTTPURL(pathToSource);
if (httpURL) {
// URL is server-relatve, so we should be able to fetch it from here.
this.#fetchText(httpURL).then(
text => sendSuccessResponse(text),
err =>
sendErrorResponse(
`Failed to fetch source url ${pathToSource}: ${err.message}`,
),
);
} else {
let file;
try {
file = fs.readFileSync(
path.resolve(this.#projectRoot, pathToSource),
'utf8',
);
} catch (err) {
sendErrorResponse(
`Failed to fetch source file ${pathToSource}: ${err.message}`,
);
}
if (file != null) {
sendSuccessResponse(file);
}
}
const text = await this.#fetchText(httpURL);
sendSuccessResponse(text);
} catch (err) {
sendErrorResponse(
`Failed to fetch source url ${pathToSource === undefined ? 'undefined' : JSON.stringify(pathToSource)} for scriptId ${req.params.scriptId}: ${err.message}`,
);
}
}
@@ -75,6 +75,9 @@ export interface InspectorProxyQueries {
* Main Inspector Proxy class that connects JavaScript VM inside Android/iOS apps and JS debugger.
*/
export default class InspectorProxy implements InspectorProxyQueries {
// Root of the project used for relative to absolute source path conversion.
#projectRoot: string;
// The base URL to the dev server from the dev-middleware host.
#serverBaseUrl: URL;
@@ -98,6 +101,7 @@ export default class InspectorProxy implements InspectorProxyQueries {
#eventLoopPerfTracker: EventLoopPerfTracker;
constructor(
projectRoot: string,
serverBaseUrl: string,
eventReporter: ?EventReporter,
experiments: Experiments,
@@ -105,6 +109,7 @@ export default class InspectorProxy implements InspectorProxyQueries {
customMessageHandler: ?CreateCustomMessageHandlerFn,
trackEventLoopPerf?: boolean = false,
) {
this.#projectRoot = projectRoot;
this.#serverBaseUrl = new URL(serverBaseUrl);
this.#devices = new Map();
this.#eventReporter = eventReporter;
@@ -350,6 +355,7 @@ export default class InspectorProxy implements InspectorProxyQueries {
name: deviceName,
app: appName,
socket,
projectRoot: this.#projectRoot,
eventReporter: this.#eventReporter,
createMessageMiddleware: this.#customMessageHandler,
deviceRelativeBaseUrl,
@@ -366,6 +372,12 @@ export default class InspectorProxy implements InspectorProxyQueries {
this.#devices.set(deviceId, newDevice);
this.#logger?.info(
"Connection established to app='%s' on device='%s'.",
appName,
deviceName,
);
debug(
"Got new device connection: name='%s', app=%s, device=%s, via=%s",
deviceName,
@@ -438,7 +450,7 @@ export default class InspectorProxy implements InspectorProxyQueries {
);
socket.on('close', (code: number, reason: string) => {
debug(
this.#logger?.info(
"Connection closed to device='%s' for app='%s' with code='%s' and reason='%s'.",
deviceName,
appName,
@@ -514,7 +526,7 @@ export default class InspectorProxy implements InspectorProxyQueries {
throw new Error(INTERNAL_ERROR_MESSAGES.UNREGISTERED_DEVICE);
}
debug(
this.#logger?.info(
"Connection established to DevTools for app='%s' on device='%s'.",
device.getApp() || 'unknown',
device.getName() || 'unknown',
@@ -582,7 +594,7 @@ export default class InspectorProxy implements InspectorProxyQueries {
});
socket.on('close', (code: number, reason: string) => {
debug(
this.#logger?.info(
"Connection closed to DevTools for app='%s' on device='%s' with code='%s' and reason='%s'.",
device.getApp() || 'unknown',
device.getName() || 'unknown',
@@ -21,7 +21,6 @@ import type {NextHandleFunction} from 'connect';
import type {IncomingMessage, ServerResponse} from 'http';
import getDevToolsFrontendUrl from '../utils/getDevToolsFrontendUrl';
import {createHash} from 'crypto';
import url from 'url';
const LEGACY_SYNTHETIC_PAGE_TITLE =
@@ -191,15 +190,11 @@ export default function openDebuggerMiddleware({
}
}
if (shouldUseStandaloneFuseboxShell) {
const windowKey = createHash('sha256')
.update(
[
serverBaseUrl,
target.webSocketDebuggerUrl,
target.appId,
].join('-'),
)
.digest('hex');
const windowKey = [
serverBaseUrl,
target.webSocketDebuggerUrl,
target.appId,
].join('-');
if (!browserLauncher.unstable_showFuseboxShell) {
throw new Error(
'Fusebox shell is not supported by the current browser launcher',
@@ -1,6 +1,6 @@
{
"name": "@react-native/eslint-config",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "ESLint config for React Native",
"license": "MIT",
"repository": {
@@ -22,7 +22,7 @@
"dependencies": {
"@babel/core": "^7.25.2",
"@babel/eslint-parser": "^7.25.1",
"@react-native/eslint-plugin": "0.83.0-main",
"@react-native/eslint-plugin": "0.82.0",
"@typescript-eslint/eslint-plugin": "^8.36.0",
"@typescript-eslint/parser": "^8.36.0",
"eslint-config-prettier": "^8.5.0",
@@ -30,7 +30,7 @@
"eslint-plugin-ft-flow": "^2.0.1",
"eslint-plugin-jest": "^29.0.1",
"eslint-plugin-react": "^7.30.1",
"eslint-plugin-react-hooks": "^7.0.1",
"eslint-plugin-react-hooks": "^5.2.0",
"eslint-plugin-react-native": "^4.0.0"
},
"peerDependencies": {
@@ -1,6 +1,6 @@
{
"name": "@react-native/eslint-plugin",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "ESLint rules for @react-native/eslint-config",
"license": "MIT",
"repository": {
+2 -2
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/eslint-plugin-specs",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "ESLint rules to validate NativeModule and Component Specs",
"license": "MIT",
"repository": {
@@ -26,7 +26,7 @@
"dependencies": {
"@babel/core": "^7.25.2",
"@babel/plugin-transform-flow-strip-types": "^7.25.2",
"@react-native/codegen": "0.83.0-main",
"@react-native/codegen": "0.82.0",
"make-dir": "^2.1.0",
"pirates": "^4.0.1",
"source-map-support": "0.5.0"
+1 -1
View File
@@ -1,6 +1,6 @@
{
"name": "@react-native/gradle-plugin",
"version": "0.83.0-main",
"version": "0.82.0",
"description": "Gradle Plugin for React Native",
"license": "MIT",
"repository": {
@@ -67,18 +67,18 @@ class ReactRootProjectPlugin : Plugin<Project> {
) {
project.logger.error(
"""
********************************************************************************
********************************************************************************
WARNING: Setting `newArchEnabled=false` in your `gradle.properties` file is not
supported anymore since React Native 0.82.
WARNING: Setting `newArchEnabled=false` in your `gradle.properties` file is not
supported anymore since React Native 0.82.
You can remove the line from your `gradle.properties` file.
The application will run with the New Architecture enabled by default.
You can remove the line from your `gradle.properties` file.
********************************************************************************
The application will run with the New Architecture enabled by default.
********************************************************************************
"""
"""
.trimIndent()
)
}
@@ -65,26 +65,25 @@ internal fun Project.configureReactTasks(variant: Variant, config: ReactExtensio
if (!isDebuggableVariant) {
val entryFileEnvVariable = System.getenv("ENTRY_FILE")
val bundleTask =
tasks.register("createBundle${targetName}JsAndAssets", BundleHermesCTask::class.java) { task
->
task.root.set(config.root)
task.nodeExecutableAndArgs.set(config.nodeExecutableAndArgs)
task.cliFile.set(cliFile)
task.bundleCommand.set(config.bundleCommand)
task.entryFile.set(detectedEntryFile(config, entryFileEnvVariable))
task.extraPackagerArgs.set(config.extraPackagerArgs)
task.bundleConfig.set(config.bundleConfig)
task.bundleAssetName.set(config.bundleAssetName)
task.jsBundleDir.set(jsBundleDir)
task.resourcesDir.set(resourcesDir)
task.hermesEnabled.set(isHermesEnabledInThisVariant)
task.minifyEnabled.set(!isHermesEnabledInThisVariant)
task.devEnabled.set(false)
task.jsIntermediateSourceMapsDir.set(jsIntermediateSourceMapsDir)
task.jsSourceMapsDir.set(jsSourceMapsDir)
task.hermesCommand.set(config.hermesCommand)
task.hermesFlags.set(config.hermesFlags)
task.reactNativeDir.set(config.reactNativeDir)
tasks.register("createBundle${targetName}JsAndAssets", BundleHermesCTask::class.java) {
it.root.set(config.root)
it.nodeExecutableAndArgs.set(config.nodeExecutableAndArgs)
it.cliFile.set(cliFile)
it.bundleCommand.set(config.bundleCommand)
it.entryFile.set(detectedEntryFile(config, entryFileEnvVariable))
it.extraPackagerArgs.set(config.extraPackagerArgs)
it.bundleConfig.set(config.bundleConfig)
it.bundleAssetName.set(config.bundleAssetName)
it.jsBundleDir.set(jsBundleDir)
it.resourcesDir.set(resourcesDir)
it.hermesEnabled.set(isHermesEnabledInThisVariant)
it.minifyEnabled.set(!isHermesEnabledInThisVariant)
it.devEnabled.set(false)
it.jsIntermediateSourceMapsDir.set(jsIntermediateSourceMapsDir)
it.jsSourceMapsDir.set(jsSourceMapsDir)
it.hermesCommand.set(config.hermesCommand)
it.hermesFlags.set(config.hermesFlags)
it.reactNativeDir.set(config.reactNativeDir)
}
variant.sources.res?.addGeneratedSourceDirectory(bundleTask, BundleHermesCTask::resourcesDir)
variant.sources.assets?.addGeneratedSourceDirectory(bundleTask, BundleHermesCTask::jsBundleDir)
@@ -94,7 +94,12 @@ abstract class BundleHermesCTask : DefaultTask() {
runCommand(bundleCommand)
if (hermesEnabled.get()) {
val detectedHermesCommand = detectOSAwareHermesCommand(root.get().asFile, hermesCommand.get())
val hermesV1Enabled =
if (project.rootProject.hasProperty("hermesV1Enabled"))
project.rootProject.findProperty("hermesV1Enabled") == "true"
else false
val detectedHermesCommand =
detectOSAwareHermesCommand(root.get().asFile, hermesCommand.get(), hermesV1Enabled)
val bytecodeFile = File("${bundleFile}.hbc")
val outputSourceMap = resolveOutputSourceMap(bundleAssetFilename)
val compilerSourceMap = resolveCompilerSourceMap(bundleAssetFilename)
@@ -168,13 +168,13 @@ abstract class GenerateAutolinkingNewArchitecturesFileTask : DefaultTask() {
# This code was generated by [React Native](https://www.npmjs.com/package/@react-native/gradle-plugin)
cmake_minimum_required(VERSION 3.13)
set(CMAKE_VERBOSE_MAKEFILE on)
# We set REACTNATIVE_MERGED_SO so libraries/apps can selectively decide to depend on either libreactnative.so
# or link against a old prefab target (this is needed for React Native 0.76 on).
set(REACTNATIVE_MERGED_SO true)
{{ libraryIncludes }}
set(AUTOLINKED_LIBRARIES
{{ libraryModules }}
)
@@ -191,28 +191,28 @@ abstract class GenerateAutolinkingNewArchitecturesFileTask : DefaultTask() {
* once the code is regenerated.
*
*/
#include "autolinking.h"
{{ autolinkingCppIncludes }}
namespace facebook {
namespace react {
std::shared_ptr<TurboModule> autolinking_ModuleProvider(const std::string moduleName, const JavaTurboModule::InitParams &params) {
{{ autolinkingCppTurboModuleJavaProviders }}
return nullptr;
}
std::shared_ptr<TurboModule> autolinking_cxxModuleProvider(const std::string moduleName, const std::shared_ptr<CallInvoker>& jsInvoker) {
{{ autolinkingCppTurboModuleCxxProviders }}
return nullptr;
}
void autolinking_registerProviders(std::shared_ptr<ComponentDescriptorProviderRegistry const> providerRegistry) {
{{ autolinkingCppComponentDescriptors }}
return;
}
} // namespace react
} // namespace facebook
"""
@@ -228,22 +228,22 @@ abstract class GenerateAutolinkingNewArchitecturesFileTask : DefaultTask() {
* once the code is regenerated.
*
*/
#pragma once
#include <ReactCommon/CallInvoker.h>
#include <ReactCommon/JavaTurboModule.h>
#include <ReactCommon/TurboModule.h>
#include <jsi/jsi.h>
#include <react/renderer/componentregistry/ComponentDescriptorProviderRegistry.h>
namespace facebook {
namespace react {
std::shared_ptr<TurboModule> autolinking_ModuleProvider(const std::string moduleName, const JavaTurboModule::InitParams &params);
std::shared_ptr<TurboModule> autolinking_cxxModuleProvider(const std::string moduleName, const std::shared_ptr<CallInvoker>& jsInvoker);
void autolinking_registerProviders(std::shared_ptr<ComponentDescriptorProviderRegistry const> providerRegistry);
} // namespace react
} // namespace facebook
"""
@@ -65,19 +65,19 @@ abstract class GenerateEntryPointTask : DefaultTask() {
val generatedFileContentsTemplate =
"""
package com.facebook.react;
import android.app.Application;
import android.content.Context;
import android.content.res.Resources;
import com.facebook.react.defaults.DefaultNewArchitectureEntryPoint;
import com.facebook.react.common.annotations.internal.LegacyArchitectureLogger;
import com.facebook.react.views.view.WindowUtilKt;
import com.facebook.react.soloader.OpenSourceMergedSoMapping;
import com.facebook.soloader.SoLoader;
import java.io.IOException;
/**
* This class is the entry point for loading React Native using the configuration
* that the users specifies in their .gradle files.
@@ -102,7 +102,7 @@ abstract class GenerateEntryPointTask : DefaultTask() {
}
}
}
"""
"""
.trimIndent()
}
}
@@ -137,61 +137,61 @@ abstract class GeneratePackageListTask : DefaultTask() {
val generatedFileContentsTemplate =
"""
package com.facebook.react;
import android.app.Application;
import android.content.Context;
import android.content.res.Resources;
import com.facebook.react.ReactPackage;
import com.facebook.react.shell.MainPackageConfig;
import com.facebook.react.shell.MainReactPackage;
import java.util.Arrays;
import java.util.ArrayList;
{{ packageImports }}
@SuppressWarnings("deprecation")
public class PackageList {
private Application application;
private ReactNativeHost reactNativeHost;
private MainPackageConfig mConfig;
public PackageList(ReactNativeHost reactNativeHost) {
this(reactNativeHost, null);
}
public PackageList(Application application) {
this(application, null);
}
public PackageList(ReactNativeHost reactNativeHost, MainPackageConfig config) {
this.reactNativeHost = reactNativeHost;
mConfig = config;
}
public PackageList(Application application, MainPackageConfig config) {
this.reactNativeHost = null;
this.application = application;
mConfig = config;
}
private ReactNativeHost getReactNativeHost() {
return this.reactNativeHost;
}
private Resources getResources() {
return this.getApplication().getResources();
}
private Application getApplication() {
if (this.reactNativeHost == null) return this.application;
return this.reactNativeHost.getApplication();
}
private Context getApplicationContext() {
return this.getApplication().getApplicationContext();
}
public ArrayList<ReactPackage> getPackages() {
return new ArrayList<>(Arrays.<ReactPackage>asList(
new MainReactPackage(mConfig){{ packageClassInstances }}
@@ -44,8 +44,12 @@ internal object AgpConfiguratorUtils {
maybeCreate("debugOptimized").apply {
manifestPlaceholders["usesCleartextTraffic"] = "true"
initWith(debug)
matchingFallbacks += listOf("release")
externalNativeBuild { cmake { arguments("-DCMAKE_BUILD_TYPE=Release") } }
externalNativeBuild {
cmake {
arguments("-DCMAKE_BUILD_TYPE=Release")
matchingFallbacks += listOf("release")
}
}
}
}
}
@@ -96,7 +100,6 @@ internal object AgpConfiguratorUtils {
project.extensions
.getByType(ApplicationAndroidComponentsExtension::class.java)
.finalizeDsl { ext ->
ext.buildFeatures.resValues = true
ext.defaultConfig.resValue(
"string",
"react_native_dev_server_ip",

Some files were not shown because too many files have changed in this diff Show More