mirror of
https://github.com/facebook/react-native.git
synced 2025-11-01 09:14:26 +00:00
Refactor: ReactHost: Delete old task creation methods (#42168)
Summary: Pull Request resolved: https://github.com/facebook/react-native/pull/42168 Changelog: [Internal] Reviewed By: mdvacca Differential Revision: D52495533 fbshipit-source-id: 787919fa68a0308d5e5bc803c7f5f1221675cd09
This commit is contained in:
committed by
Facebook GitHub Bot
parent
2e6afdc550
commit
af004ce4e6
+40
-299
@@ -67,7 +67,6 @@ import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.Callable;
|
||||
import java.util.concurrent.Executor;
|
||||
import java.util.concurrent.Executors;
|
||||
import java.util.concurrent.atomic.AtomicInteger;
|
||||
@@ -201,12 +200,7 @@ public class ReactHostImpl implements ReactHost {
|
||||
*/
|
||||
@Override
|
||||
public TaskInterface<Void> start() {
|
||||
if (ReactFeatureFlags.enableBridgelessArchitectureNewCreateReloadDestroy) {
|
||||
return Task.call(this::newGetOrCreateStartTask, mBGExecutor)
|
||||
.continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
return Task.call(this::oldGetOrCreateStartTask, mBGExecutor).continueWithTask(Task::getResult);
|
||||
return Task.call(this::newGetOrCreateStartTask, mBGExecutor).continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
/** Initialize and run a React Native surface in a background without mounting real views. */
|
||||
@@ -441,36 +435,32 @@ public class ReactHostImpl implements ReactHost {
|
||||
@Override
|
||||
public TaskInterface<Void> reload(String reason) {
|
||||
final String method = "reload()";
|
||||
if (ReactFeatureFlags.enableBridgelessArchitectureNewCreateReloadDestroy) {
|
||||
return Task.call(
|
||||
() -> {
|
||||
Task<Void> reloadTask = null;
|
||||
if (mDestroyTask != null) {
|
||||
log(method, "Waiting for destroy to finish, before reloading React Native.");
|
||||
reloadTask =
|
||||
mDestroyTask
|
||||
.continueWithTask(task -> newGetOrCreateReloadTask(reason), mBGExecutor)
|
||||
.makeVoid();
|
||||
} else {
|
||||
reloadTask = newGetOrCreateReloadTask(reason).makeVoid();
|
||||
}
|
||||
return Task.call(
|
||||
() -> {
|
||||
Task<Void> reloadTask = null;
|
||||
if (mDestroyTask != null) {
|
||||
log(method, "Waiting for destroy to finish, before reloading React Native.");
|
||||
reloadTask =
|
||||
mDestroyTask
|
||||
.continueWithTask(task -> newGetOrCreateReloadTask(reason), mBGExecutor)
|
||||
.makeVoid();
|
||||
} else {
|
||||
reloadTask = newGetOrCreateReloadTask(reason).makeVoid();
|
||||
}
|
||||
|
||||
return reloadTask.continueWithTask(
|
||||
task -> {
|
||||
if (task.isFaulted()) {
|
||||
mReactHostDelegate.handleInstanceException(task.getError());
|
||||
return newGetOrCreateDestroyTask("Reload failed", task.getError());
|
||||
}
|
||||
return reloadTask.continueWithTask(
|
||||
task -> {
|
||||
if (task.isFaulted()) {
|
||||
mReactHostDelegate.handleInstanceException(task.getError());
|
||||
return newGetOrCreateDestroyTask("Reload failed", task.getError());
|
||||
}
|
||||
|
||||
return task;
|
||||
},
|
||||
mBGExecutor);
|
||||
},
|
||||
mBGExecutor)
|
||||
.continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
return oldReload(reason);
|
||||
return task;
|
||||
},
|
||||
mBGExecutor);
|
||||
},
|
||||
mBGExecutor)
|
||||
.continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -486,24 +476,19 @@ public class ReactHostImpl implements ReactHost {
|
||||
@Override
|
||||
public TaskInterface<Void> destroy(String reason, @Nullable Exception ex) {
|
||||
final String method = "destroy()";
|
||||
if (ReactFeatureFlags.enableBridgelessArchitectureNewCreateReloadDestroy) {
|
||||
return Task.call(
|
||||
() -> {
|
||||
if (mReloadTask != null) {
|
||||
log(
|
||||
method,
|
||||
"Reloading React Native. Waiting for reload to finish before destroying React Native.");
|
||||
return mReloadTask.continueWithTask(
|
||||
task -> newGetOrCreateDestroyTask(reason, ex), mBGExecutor);
|
||||
}
|
||||
return newGetOrCreateDestroyTask(reason, ex);
|
||||
},
|
||||
mBGExecutor)
|
||||
.continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
oldDestroy(reason, ex);
|
||||
return Task.forResult(nullsafeFIXME(null, "Empty Destroy Task"));
|
||||
return Task.call(
|
||||
() -> {
|
||||
if (mReloadTask != null) {
|
||||
log(
|
||||
method,
|
||||
"Reloading React Native. Waiting for reload to finish before destroying React Native.");
|
||||
return mReloadTask.continueWithTask(
|
||||
task -> newGetOrCreateDestroyTask(reason, ex), mBGExecutor);
|
||||
}
|
||||
return newGetOrCreateDestroyTask(reason, ex);
|
||||
},
|
||||
mBGExecutor)
|
||||
.continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
private MemoryPressureListener createMemoryPressureListener(ReactInstance reactInstance) {
|
||||
@@ -720,30 +705,6 @@ public class ReactHostImpl implements ReactHost {
|
||||
@ThreadConfined("ReactHost")
|
||||
private @Nullable Task<Void> mStartTask = null;
|
||||
|
||||
@ThreadConfined("ReactHost")
|
||||
private Task<Void> oldGetOrCreateStartTask() {
|
||||
if (mStartTask == null) {
|
||||
final String method = "oldGetOrCreateStartTask()";
|
||||
log(method, "Schedule");
|
||||
mStartTask =
|
||||
getOrCreateReactInstance()
|
||||
.continueWithTask(
|
||||
task -> {
|
||||
if (task.isFaulted()) {
|
||||
destroy(
|
||||
"oldGetOrCreateStartTask() failure: " + task.getError().getMessage(),
|
||||
task.getError());
|
||||
mReactHostDelegate.handleInstanceException(task.getError());
|
||||
}
|
||||
|
||||
return task;
|
||||
},
|
||||
mBGExecutor)
|
||||
.makeVoid();
|
||||
}
|
||||
return mStartTask;
|
||||
}
|
||||
|
||||
@ThreadConfined("ReactHost")
|
||||
private Task<Void> newGetOrCreateStartTask() {
|
||||
if (mStartTask == null) {
|
||||
@@ -857,12 +818,8 @@ public class ReactHostImpl implements ReactHost {
|
||||
* destroying, will wait until destroy is finished, before creating.
|
||||
*/
|
||||
private Task<ReactInstance> getOrCreateReactInstance() {
|
||||
if (ReactFeatureFlags.enableBridgelessArchitectureNewCreateReloadDestroy) {
|
||||
return Task.call(this::waitThenCallNewGetOrCreateReactInstanceTask, mBGExecutor)
|
||||
.continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
return oldGetOrCreateReactInstanceTask();
|
||||
return Task.call(this::waitThenCallNewGetOrCreateReactInstanceTask, mBGExecutor)
|
||||
.continueWithTask(Task::getResult);
|
||||
}
|
||||
|
||||
@ThreadConfined("ReactHost")
|
||||
@@ -1021,87 +978,6 @@ public class ReactHostImpl implements ReactHost {
|
||||
});
|
||||
}
|
||||
|
||||
private Task<ReactInstance> oldGetOrCreateReactInstanceTask() {
|
||||
final String method = "oldGetOrCreateReactInstanceTask()";
|
||||
log(method);
|
||||
|
||||
return mReactInstanceTaskRef.getOrCreate(
|
||||
() -> {
|
||||
log(method, "Start");
|
||||
ReactMarker.logMarker(
|
||||
ReactMarkerConstants.REACT_BRIDGELESS_LOADING_START, BRIDGELESS_MARKER_INSTANCE_KEY);
|
||||
|
||||
final BridgelessReactContext reactContext = getOrCreateReactContext();
|
||||
final DevSupportManager devSupportManager = getDevSupportManager();
|
||||
reactContext.setJSExceptionHandler(devSupportManager);
|
||||
|
||||
return getJsBundleLoader()
|
||||
.onSuccess(
|
||||
task -> {
|
||||
final JSBundleLoader bundleLoader = task.getResult();
|
||||
log(method, "Creating ReactInstance");
|
||||
final ReactInstance instance =
|
||||
new ReactInstance(
|
||||
reactContext,
|
||||
mReactHostDelegate,
|
||||
mComponentFactory,
|
||||
devSupportManager,
|
||||
mQueueThreadExceptionHandler,
|
||||
mReactJsExceptionHandler,
|
||||
mUseDevSupport);
|
||||
|
||||
if (ReactFeatureFlags
|
||||
.unstable_bridgelessArchitectureMemoryPressureHackyBoltsFix) {
|
||||
mMemoryPressureListener = createMemoryPressureListener(instance);
|
||||
}
|
||||
mMemoryPressureRouter.addMemoryPressureListener(mMemoryPressureListener);
|
||||
|
||||
log(method, "Loading JS Bundle");
|
||||
instance.loadJSBundle(bundleLoader);
|
||||
|
||||
log(
|
||||
method,
|
||||
"Calling DevSupportManagerBase.onNewReactContextCreated(reactContext)");
|
||||
devSupportManager.onNewReactContextCreated(reactContext);
|
||||
reactContext.runOnJSQueueThread(
|
||||
() -> {
|
||||
// Executing on the JS thread to ensurethat we're done
|
||||
// loading the JS bundle.
|
||||
// TODO T76081936 Move this if we switchto a sync RTE
|
||||
ReactMarker.logMarker(
|
||||
ReactMarkerConstants.REACT_BRIDGELESS_LOADING_END,
|
||||
BRIDGELESS_MARKER_INSTANCE_KEY);
|
||||
});
|
||||
return instance;
|
||||
},
|
||||
mBGExecutor)
|
||||
.onSuccess(
|
||||
task -> {
|
||||
/*
|
||||
Call ReactContext.onHostResume() only when already in the resumed state which
|
||||
aligns with the bridge https://fburl.com/diffusion/2qhxmudv.
|
||||
*/
|
||||
mReactLifecycleStateManager.resumeReactContextIfHostResumed(
|
||||
reactContext, getCurrentActivity());
|
||||
|
||||
ReactInstanceEventListener[] listeners =
|
||||
new ReactInstanceEventListener[mReactInstanceEventListeners.size()];
|
||||
final ReactInstanceEventListener[] finalListeners =
|
||||
mReactInstanceEventListeners.toArray(listeners);
|
||||
|
||||
log(method, "Executing ReactInstanceEventListeners");
|
||||
for (ReactInstanceEventListener listener : finalListeners) {
|
||||
if (listener != null) {
|
||||
listener.onReactContextInitialized(reactContext);
|
||||
}
|
||||
}
|
||||
|
||||
return task.getResult();
|
||||
},
|
||||
mUIExecutor);
|
||||
});
|
||||
}
|
||||
|
||||
private Task<JSBundleLoader> getJsBundleLoader() {
|
||||
final String method = "getJSBundleLoader()";
|
||||
log(method);
|
||||
@@ -1604,141 +1480,6 @@ public class ReactHostImpl implements ReactHost {
|
||||
return mDestroyTask;
|
||||
}
|
||||
|
||||
/** Destroy and recreate the ReactInstance and context. */
|
||||
private Task<Void> oldReload(String reason) {
|
||||
final String method = "oldReload()";
|
||||
log(method);
|
||||
|
||||
// Log how React Native is destroyed
|
||||
// TODO(T136397487): Remove after Venice is shipped to 100%
|
||||
raiseSoftException(method, reason);
|
||||
|
||||
synchronized (mReactInstanceTaskRef) {
|
||||
mMemoryPressureRouter.removeMemoryPressureListener(mMemoryPressureListener);
|
||||
oldDestroyReactInstanceAndContext(method, reason);
|
||||
|
||||
return callAfterGetOrCreateReactInstance(
|
||||
method,
|
||||
reactInstance -> {
|
||||
// Restart any attached surfaces
|
||||
log(method, "Restarting Surfaces");
|
||||
synchronized (mAttachedSurfaces) {
|
||||
for (ReactSurfaceImpl surface : mAttachedSurfaces) {
|
||||
reactInstance.startSurface(surface);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
/** Destroy the specified instance and context. */
|
||||
private void oldDestroy(String reason, @Nullable Exception ex) {
|
||||
final String method = "oldDestroy()";
|
||||
log(method);
|
||||
|
||||
// Log how React Native is destroyed
|
||||
// TODO(T136397487): Remove after Venice is shipped to 100%
|
||||
raiseSoftException(method, reason, ex);
|
||||
|
||||
synchronized (mReactInstanceTaskRef) {
|
||||
// Prevent re-destroy when ReactInstance has been reset already, which could happen when
|
||||
// calling destroy multiple times on the same thread
|
||||
ReactInstance reactInstance = mReactInstanceTaskRef.get().getResult();
|
||||
if (reactInstance == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Retain a reference to current ReactContext before de-referenced by mReactContextRef
|
||||
final ReactContext reactContext = getCurrentReactContext();
|
||||
|
||||
if (reactContext != null) {
|
||||
mMemoryPressureRouter.destroy(reactContext);
|
||||
}
|
||||
|
||||
oldDestroyReactInstanceAndContext(method, reason);
|
||||
|
||||
// Remove all attached surfaces
|
||||
log(method, "Clearing attached surfaces");
|
||||
synchronized (mAttachedSurfaces) {
|
||||
mAttachedSurfaces.clear();
|
||||
}
|
||||
|
||||
Task.call(
|
||||
(Callable<Void>)
|
||||
() -> {
|
||||
moveToHostDestroy(reactContext);
|
||||
return null;
|
||||
},
|
||||
mUIExecutor);
|
||||
}
|
||||
}
|
||||
|
||||
private void oldDestroyReactInstanceAndContext(final String callingMethod, final String reason) {
|
||||
final String method = "oldDestroyReactInstanceAndContext(" + callingMethod + ")";
|
||||
log(method);
|
||||
|
||||
synchronized (mReactInstanceTaskRef) {
|
||||
Task<ReactInstance> task = mReactInstanceTaskRef.getAndReset();
|
||||
if (!task.isFaulted() && !task.isCancelled()) {
|
||||
final ReactInstance instance = task.getResult();
|
||||
|
||||
// Noop on redundant calls to destroyReactInstance()
|
||||
if (instance == null) {
|
||||
log(method, "ReactInstance is null");
|
||||
return;
|
||||
}
|
||||
|
||||
/*
|
||||
* The surfaces should be stopped before the instance destroy.
|
||||
* Calling stop directly on instance ensures we keep the list of attached surfaces for restart.
|
||||
*/
|
||||
log(method, "Stopping surfaces");
|
||||
synchronized (mAttachedSurfaces) {
|
||||
for (ReactSurfaceImpl surface : mAttachedSurfaces) {
|
||||
instance.stopSurface(surface);
|
||||
surface.clear();
|
||||
}
|
||||
}
|
||||
|
||||
ReactContext reactContext = getCurrentReactContext();
|
||||
|
||||
// Reset the ReactContext inside the DevSupportManager
|
||||
if (reactContext != null) {
|
||||
log(method, "DevSupportManager.onReactInstanceDestroyed()");
|
||||
getDevSupportManager().onReactInstanceDestroyed(reactContext);
|
||||
log(method, "Destroy ReactContext");
|
||||
mBridgelessReactContextRef.reset();
|
||||
}
|
||||
|
||||
mBGExecutor.execute(
|
||||
() -> {
|
||||
// instance.destroy() is time consuming and is confined to ReactHost thread.
|
||||
log(method, "Destroy ReactInstance");
|
||||
instance.destroy();
|
||||
|
||||
// Re-enable preloads
|
||||
log(method, "Resetting Preload task ref");
|
||||
mStartTask = null;
|
||||
});
|
||||
} else {
|
||||
raiseSoftException(
|
||||
method,
|
||||
("Not cleaning up ReactInstance: task.isFaulted() = "
|
||||
+ task.isFaulted()
|
||||
+ ", task.isCancelled() = "
|
||||
+ task.isCancelled())
|
||||
+ ". Reason: "
|
||||
+ reason);
|
||||
|
||||
mBGExecutor.execute(
|
||||
() -> {
|
||||
log(method, "Resetting Preload task ref");
|
||||
mStartTask = null;
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public JSEngineResolutionAlgorithm getJsEngineResolutionAlgorithm() {
|
||||
|
||||
Reference in New Issue
Block a user