Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix: RedBoxes don't always show up after React Native destroys #38997

Closed
wants to merge 5 commits into from

Conversation

RSNara
Copy link
Contributor

@RSNara RSNara commented Aug 14, 2023

Summary:
After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

Problem

React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

Changes

This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

@facebook-github-bot facebook-github-bot added CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. p: Facebook Partner: Facebook Partner labels Aug 14, 2023
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 14, 2023
…ook#38997)

Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

fbshipit-source-id: d74bf4770546ab3a5940b8fac1b1d20f168e7100
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 14, 2023
…ook#38997)

Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

fbshipit-source-id: 80ae35ea3b6471d57a52c4ac30192bc0e368c35f
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 14, 2023
…ook#38997)

Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

fbshipit-source-id: 1be9aeb597bc9b7216df5d7ade86f8e3076533f9
@analysis-bot
Copy link

analysis-bot commented Aug 14, 2023

Platform Engine Arch Size (bytes) Diff
android hermes arm64-v8a 8,948,936 +25
android hermes armeabi-v7a n/a --
android hermes x86 n/a --
android hermes x86_64 n/a --
android jsc arm64-v8a 9,543,086 +871
android jsc armeabi-v7a n/a --
android jsc x86 n/a --
android jsc x86_64 n/a --

Base commit: f4f1894
Branch: main

@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 14, 2023
…ook#38997)

Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

fbshipit-source-id: 19b0e3345f6a2f663572798dc3b914cb4bad749d
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 14, 2023
…ook#38997)

Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

fbshipit-source-id: ac34981183fd9a6c6010d36069d0bb4a85a5c12c
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 15, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

fbshipit-source-id: 2ef5ff555b93a802c399143d16b377ff5b6d8a67
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 15, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 4c0260b77dec7d75648be1da5b05f5d6438306fb
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 15, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: D48076893

fbshipit-source-id: 1a6f2b14cb5244335d6d4d3749bbd5ffcab08b93
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Reviewed By: mdvacca

Differential Revision: D48076893

fbshipit-source-id: 510ad7176c4f4547d805ca2093a5be19eb7c985b
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: bac85461fed61f7cd3b8adca7c1770ebf49689ae
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 98fed2b0c2a9f5f1a44850ca0653e359db2f9155
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: d0263e345b3c1d1c636a7d47f40c74ce7fa222ad
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: d4372a0b4d1063344142a3d5f66da7ae62f2ff87
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 52bcc8074d4ccf707fc75b706c46873d8210e789
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Reviewed By: mdvacca

Differential Revision: D48076893

fbshipit-source-id: 60bc61fe6c78146ae4b6025aaefb010f1e15a2e4
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 4f06527d7570b212e2bca985dc04912741fa9830
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 3ddf2c89703b469d8b3515eb36847f906c74e270
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Reviewed By: mdvacca

Differential Revision: D48076893

fbshipit-source-id: 7e3f7f5cca1dcfd9ce9cfe5587dadb2324707881
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 0658ee2ac9b1601c9b94309527f3f8e475f3d7a0
…ebook#39001)

Summary:
Pull Request resolved: facebook#39001

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076894

fbshipit-source-id: 670dfa49d9fafebbea43ce77925eb990df0b5b4d
Summary:
During React Native teardown, we should stop all React surfaces. Otherwise, the app could crash with this error:

```
08-06 14:54:08.644 14843 14843 F DEBUG   : Abort message: 'xplat/js/react-native-github/packages/react-native/ReactCommon/react/renderer/scheduler/Scheduler.cpp:171: function ~Scheduler: assertion failed (surfaceIds.empty() && "Scheduler was destroyed with outstanding Surfaces.")'
```

When can teardown occur? One case: an exception occurs on the NativeModules thread.

NOTE: This diff impacts the **new** Bridgeless mode lifecycle methods.

Changelog: [Internal]

Differential Revision: https://internalfb.com/D47926966

fbshipit-source-id: 60d0aa032c9eecbf7d4b1181c0675d96ea338232
…ebook#38999)

Summary:
Pull Request resolved: facebook#38999

After React Native tears down, a RedBox can appear, prompting the user to reload.

**Problem:** After React Native reloads, the React Native screen wouldn't show up.

**Cause:** ReactContext.onHostResume() wasn't executed.

Why:
- React Native teardown moves the React manager into the **onHostDestroy()** state.
- During initialization, React Native only calls ReactContext.onHostResume(), if the React manager was *already* in the **onHostResume()** state.

https://www.internalfb.com/code/fbsource/[f82938c7cc9a0ee722c85c33d1027f326049d37c]/xplat/js/react-native-github/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridgeless/ReactHost.java?lines=924-925

**Question:** Why does React Native only call ReactContext.onHostResume(), **if the React manager was already in the onHostResume() state?**

In short, we want ReactContext.onHostResume() to be delayed until the user navigates to the first React Native screen. Please read the comments in the code to understand why.

## The fix
If we're initializing React Native during a reload, just always call ReactContext.onHostResume().

If React Native is reloading, it seems reasonable to assume that:
1. We must have navigated to a React Native screen in the past, or
2. We must be on a React Native screen.

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076895

fbshipit-source-id: df2caeab9a98f543b8479463ada6c8fbdbc046cf
Summary:
Pull Request resolved: facebook#38998

Instead of using the mActivity reference directly, let's just use getCurrentActivity() and setCurrentActivity().

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076896

fbshipit-source-id: 7a8ab56037429c9221d23cc603d89f0dd883b099
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Reviewed By: mdvacca

Differential Revision: D48076893

fbshipit-source-id: c75f8b8c6e50e62414a4d5acd374af283dda7459
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 35fa32af1bf4fee1e9277b2fc05cb7cdadad2027
@facebook-github-bot
Copy link
Contributor

This pull request was exported from Phabricator. Differential Revision: D48076893

RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 94a5916a6f4b612c96105cc39079f80a430bf3eb
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: 138db3ba949679cb099526b34f2543ee3ec04346
RSNara added a commit to RSNara/react-native that referenced this pull request Aug 21, 2023
Summary:
Pull Request resolved: facebook#38997

After React Native gets destroyed (e.g: via an exception), the ReactHost resets its current activity.

## Problem
React Native can display RedBoxes after React Native destruction (e.g: in the case of an exception).

Displaying RedBoxes requires the current activity, which gets nullified. So, the RedBox might not show up after destruction.

## Changes
This diff makes ReactHost keep a track of its last non-null activity in a WeakRef.
Then, the DevMenu just uses the last non-null activity to display RedBoxes (and everything else).

Changelog: [Internal]

Differential Revision: https://internalfb.com/D48076893

fbshipit-source-id: c53113b33d2aee77f5b695d428d0f4b076f38503
@facebook-github-bot facebook-github-bot added the Merged This PR has been merged. label Aug 21, 2023
@facebook-github-bot
Copy link
Contributor

This pull request has been merged in 1f0094e.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
CLA Signed This label is managed by the Facebook bot. Authors need to sign the CLA before a PR can be reviewed. fb-exported Merged This PR has been merged. p: Facebook Partner: Facebook Partner
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants