mirror of
https://github.com/facebook/react-native.git
synced 2025-11-01 09:14:26 +00:00
Schedule OnViewAttachMountItems in GuardedRunnable (#52143)
Summary: Pull Request resolved: https://github.com/facebook/react-native/pull/52143 Noticed that some of the `IndexOutOfBoundsException` crashes we've been tracking we're not being reported as soft errors because they were not running wrapped by the RN ExceptionHandler Changelog: [Internal] Reviewed By: lenaic Differential Revision: D77017423 fbshipit-source-id: 760297a0c5ee3d58577931829a31d312dacffdf1
This commit is contained in:
committed by
Facebook GitHub Bot
parent
e297fe1582
commit
ffb37373ba
+49
-50
@@ -21,6 +21,7 @@ import androidx.collection.SparseArrayCompat;
|
||||
import com.facebook.common.logging.FLog;
|
||||
import com.facebook.infer.annotation.Assertions;
|
||||
import com.facebook.infer.annotation.ThreadConfined;
|
||||
import com.facebook.react.bridge.GuardedRunnable;
|
||||
import com.facebook.react.bridge.ReactNoCrashSoftException;
|
||||
import com.facebook.react.bridge.ReactSoftExceptionLogger;
|
||||
import com.facebook.react.bridge.ReadableArray;
|
||||
@@ -189,57 +190,55 @@ public class SurfaceMountingManager {
|
||||
mTagToViewState.put(mSurfaceId, new ViewState(mSurfaceId, rootView, mRootViewManager, true));
|
||||
|
||||
Runnable runnable =
|
||||
() -> {
|
||||
// The CPU has ticked since `addRootView` was called, so the surface could technically
|
||||
// have already stopped here.
|
||||
if (isStopped()) {
|
||||
return;
|
||||
new GuardedRunnable(Assertions.assertNotNull(mThemedReactContext)) {
|
||||
@Override
|
||||
public void runGuarded() {
|
||||
// The CPU has ticked since `addRootView` was called, so the surface could technically
|
||||
// have already stopped here.
|
||||
if (isStopped()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (rootView.getId() == mSurfaceId) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Race condition in addRootView detected. Trying to set an id of ["
|
||||
+ mSurfaceId
|
||||
+ "] on the RootView, but that id has already been set. "));
|
||||
} else if (rootView.getId() != View.NO_ID) {
|
||||
FLog.e(
|
||||
TAG,
|
||||
"Trying to add RootTag to RootView that already has a tag: existing tag: [%d] new"
|
||||
+ " tag: [%d]",
|
||||
rootView.getId(),
|
||||
mSurfaceId);
|
||||
// This behavior can not be guaranteed in hybrid apps that have a native android layer
|
||||
// over which reactRootViews are added and the native views need to have ids on them
|
||||
// in order to work. Hence this can cause unnecessary crashes at runtime for hybrid
|
||||
// apps. So converting this to a soft exception such that pure react-native devs can
|
||||
// still see the warning while hybrid apps continue to run without crashes
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Trying to add a root view with an explicit id already set. React Native uses"
|
||||
+ " the id field to track react tags and will overwrite this field. If"
|
||||
+ " that is fine, explicitly overwrite the id field to View.NO_ID before"
|
||||
+ " calling addRootView."));
|
||||
}
|
||||
rootView.setId(mSurfaceId);
|
||||
|
||||
if (rootView instanceof ReactRoot) {
|
||||
((ReactRoot) rootView).setRootViewTag(mSurfaceId);
|
||||
}
|
||||
|
||||
executeMountItemsOnViewAttach();
|
||||
|
||||
// By doing this after `executeMountItemsOnViewAttach`, we ensure that any operations
|
||||
// scheduled while processing this queue are also added to the queue, instead of being
|
||||
// processed immediately through the queue in `MountItemDispatcher`.
|
||||
mRootViewAttached = true;
|
||||
}
|
||||
|
||||
if (rootView.getId() == mSurfaceId) {
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Race condition in addRootView detected. Trying to set an id of ["
|
||||
+ mSurfaceId
|
||||
+ "] on the RootView, but that id has already been set. "));
|
||||
} else if (rootView.getId() != View.NO_ID) {
|
||||
FLog.e(
|
||||
TAG,
|
||||
"Trying to add RootTag to RootView that already has a tag: existing tag: [%d] new"
|
||||
+ " tag: [%d]",
|
||||
rootView.getId(),
|
||||
mSurfaceId);
|
||||
// This behavior can not be guaranteed in hybrid apps that have a native android layer
|
||||
// over
|
||||
// which reactRootViews are added and the native views need to have ids on them in order
|
||||
// to
|
||||
// work.
|
||||
// Hence this can cause unnecessary crashes at runtime for hybrid apps.
|
||||
// So converting this to a soft exception such that pure react-native devs can still see
|
||||
// the
|
||||
// warning while hybrid apps continue to run without crashes
|
||||
ReactSoftExceptionLogger.logSoftException(
|
||||
TAG,
|
||||
new IllegalViewOperationException(
|
||||
"Trying to add a root view with an explicit id already set. React Native uses"
|
||||
+ " the id field to track react tags and will overwrite this field. If that"
|
||||
+ " is fine, explicitly overwrite the id field to View.NO_ID before calling"
|
||||
+ " addRootView."));
|
||||
}
|
||||
rootView.setId(mSurfaceId);
|
||||
|
||||
if (rootView instanceof ReactRoot) {
|
||||
((ReactRoot) rootView).setRootViewTag(mSurfaceId);
|
||||
}
|
||||
|
||||
executeMountItemsOnViewAttach();
|
||||
|
||||
// By doing this after `executeMountItemsOnViewAttach`, we ensure
|
||||
// that any operations scheduled while processing this queue are
|
||||
// also added to the queue, instead of being processed immediately
|
||||
// through the queue in `MountItemDispatcher`.
|
||||
mRootViewAttached = true;
|
||||
};
|
||||
|
||||
if (UiThreadUtil.isOnUiThread()) {
|
||||
|
||||
Reference in New Issue
Block a user