AppStateModule should verify that Catalyst is alive before getting a JS module
Summary: AppStateModule can be called indirectly when the ReactContext is torn down. Trying to get a JS module at this time will result in a crash if the ReactContext has already torn down Catalyst. Check explicitly that Catalyst is still alive before trying to emit an event to JS via some JS module. Changelog: [Internal] Reviewed By: ejanzer, mdvacca Differential Revision: D17969056 fbshipit-source-id: dd446de57280e588a73f3e228bac82b3d67ecdc0
This commit is contained in:
Родитель
f8bf65b8fd
Коммит
46a28e5460
|
@ -7,23 +7,28 @@
|
|||
|
||||
package com.facebook.react.modules.appstate;
|
||||
|
||||
import android.util.Log;
|
||||
import com.facebook.react.bridge.Arguments;
|
||||
import com.facebook.react.bridge.Callback;
|
||||
import com.facebook.react.bridge.LifecycleEventListener;
|
||||
import com.facebook.react.bridge.ReactApplicationContext;
|
||||
import com.facebook.react.bridge.ReactContextBaseJavaModule;
|
||||
import com.facebook.react.bridge.ReactMethod;
|
||||
import com.facebook.react.bridge.ReactSoftException;
|
||||
import com.facebook.react.bridge.WindowFocusChangeListener;
|
||||
import com.facebook.react.bridge.WritableMap;
|
||||
import com.facebook.react.common.LifecycleState;
|
||||
import com.facebook.react.common.build.ReactBuildConfig;
|
||||
import com.facebook.react.module.annotations.ReactModule;
|
||||
import com.facebook.react.modules.core.DeviceEventManagerModule.RCTDeviceEventEmitter;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
@ReactModule(name = AppStateModule.NAME)
|
||||
public class AppStateModule extends ReactContextBaseJavaModule
|
||||
implements LifecycleEventListener, WindowFocusChangeListener {
|
||||
public static final String TAG = AppStateModule.class.getSimpleName();
|
||||
|
||||
public static final String NAME = "AppState";
|
||||
|
||||
|
@ -81,9 +86,7 @@ public class AppStateModule extends ReactContextBaseJavaModule
|
|||
|
||||
@Override
|
||||
public void onWindowFocusChange(boolean hasFocus) {
|
||||
getReactApplicationContext()
|
||||
.getJSModule(RCTDeviceEventEmitter.class)
|
||||
.emit("appStateFocusChange", hasFocus);
|
||||
sendEvent("appStateFocusChange", hasFocus);
|
||||
}
|
||||
|
||||
private WritableMap createAppStateEventMap() {
|
||||
|
@ -92,9 +95,26 @@ public class AppStateModule extends ReactContextBaseJavaModule
|
|||
return appState;
|
||||
}
|
||||
|
||||
private void sendEvent(String eventName, @Nullable Object data) {
|
||||
ReactApplicationContext reactApplicationContext = getReactApplicationContext();
|
||||
|
||||
if (reactApplicationContext.hasActiveCatalystInstance()) {
|
||||
reactApplicationContext.getJSModule(RCTDeviceEventEmitter.class).emit(eventName, data);
|
||||
} else {
|
||||
// We want to collect data about how often this happens, but this will cause a crash
|
||||
// in debug, which isn't desirable.
|
||||
String msg =
|
||||
"sendAppStateChangeEvent: trying to update app state when Catalyst Instance has already disappeared: "
|
||||
+ eventName;
|
||||
if (ReactBuildConfig.DEBUG) {
|
||||
Log.e(AppStateModule.TAG, msg);
|
||||
} else {
|
||||
ReactSoftException.logSoftException(AppStateModule.TAG, new RuntimeException(msg));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void sendAppStateChangeEvent() {
|
||||
getReactApplicationContext()
|
||||
.getJSModule(RCTDeviceEventEmitter.class)
|
||||
.emit("appStateDidChange", createAppStateEventMap());
|
||||
sendEvent("appStateDidChange", createAppStateEventMap());
|
||||
}
|
||||
}
|
||||
|
|
Загрузка…
Ссылка в новой задаче