From 81d22684de1cf71d7e42ee18a12a5cdc3b30a248 Mon Sep 17 00:00:00 2001 From: Nicola Corti Date: Mon, 4 Nov 2024 08:26:23 -0800 Subject: [PATCH] Stable API - Make InteropModuleRegistry internal (#47374) Summary: Pull Request resolved: https://github.com/facebook/react-native/pull/47374 I've converted this class to Kotlin + made it `internal` as it should not be exposed publicly. This class is part of the iterop layer for the New Architecture. Marked as breaking but I expect no meaningful breakages here. Changelog: [Android] [Breaking] - Stable API - Make InteropModuleRegistry internal Reviewed By: javache Differential Revision: D65421965 --- .../ReactAndroid/api/ReactAndroid.api | 7 --- .../facebook/react/bridge/ReactContext.java | 2 + .../bridge/interop/InteropModuleRegistry.java | 57 ------------------- .../bridge/interop/InteropModuleRegistry.kt | 49 ++++++++++++++++ .../interop/InteropModuleRegistryTest.kt | 2 +- 5 files changed, 52 insertions(+), 65 deletions(-) delete mode 100644 packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.java create mode 100644 packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.kt diff --git a/packages/react-native/ReactAndroid/api/ReactAndroid.api b/packages/react-native/ReactAndroid/api/ReactAndroid.api index e6594e975793..029dbdb47213 100644 --- a/packages/react-native/ReactAndroid/api/ReactAndroid.api +++ b/packages/react-native/ReactAndroid/api/ReactAndroid.api @@ -1644,13 +1644,6 @@ public final class com/facebook/react/bridge/WritableNativeMap : com/facebook/re public fun putString (Ljava/lang/String;Ljava/lang/String;)V } -public class com/facebook/react/bridge/interop/InteropModuleRegistry { - public fun ()V - public fun getInteropModule (Ljava/lang/Class;)Lcom/facebook/react/bridge/JavaScriptModule; - public fun registerInteropModule (Ljava/lang/Class;Ljava/lang/Object;)V - public fun shouldReturnInteropModule (Ljava/lang/Class;)Z -} - public abstract interface class com/facebook/react/bridge/queue/MessageQueueThread { public abstract fun assertIsOnThread ()V public abstract fun assertIsOnThread (Ljava/lang/String;)V diff --git a/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java b/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java index c67274d3be6f..8fd31df9675a 100644 --- a/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java +++ b/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/ReactContext.java @@ -63,6 +63,8 @@ public interface RCTDeviceEventEmitter extends JavaScriptModule { private @Nullable JSExceptionHandler mExceptionHandlerWrapper; private @Nullable WeakReference mCurrentActivity; + // NOTE: When converted to Kotlin, this field should be made internal due to + // visibility restriction on InteropModuleRegistry otherwise it will be exposed to the public API. protected @Nullable InteropModuleRegistry mInteropModuleRegistry; private boolean mIsInitialized = false; diff --git a/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.java b/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.java deleted file mode 100644 index 344bc7a14517..000000000000 --- a/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.java +++ /dev/null @@ -1,57 +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. - */ - -package com.facebook.react.bridge.interop; - -import androidx.annotation.Nullable; -import com.facebook.react.bridge.JavaScriptModule; -import com.facebook.react.internal.featureflags.ReactNativeFeatureFlags; -import java.util.HashMap; - -/** - * A utility class that takes care of returning {@link JavaScriptModule} which are used for the - * Fabric Interop Layer. This allows us to override the returned classes once the user is invoking - * `ReactContext.getJsModule()`. - * - *

Currently we only support a `RCTEventEmitter` re-implementation, being `InteropEventEmitter` - * but this class can support other re-implementation in the future. - */ -public class InteropModuleRegistry { - - @SuppressWarnings("rawtypes") - private final HashMap supportedModules; - - public InteropModuleRegistry() { - supportedModules = new HashMap<>(); - } - - public boolean shouldReturnInteropModule(Class requestedModule) { - return checkReactFeatureFlagsConditions() && supportedModules.containsKey(requestedModule); - } - - @Nullable - public T getInteropModule(Class requestedModule) { - if (checkReactFeatureFlagsConditions()) { - //noinspection unchecked - return (T) supportedModules.get(requestedModule); - } else { - return null; - } - } - - public void registerInteropModule( - Class interopModuleInterface, Object interopModule) { - if (checkReactFeatureFlagsConditions()) { - supportedModules.put(interopModuleInterface, interopModule); - } - } - - private boolean checkReactFeatureFlagsConditions() { - return ReactNativeFeatureFlags.enableFabricRenderer() - && ReactNativeFeatureFlags.useFabricInterop(); - } -} diff --git a/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.kt b/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.kt new file mode 100644 index 000000000000..9805b229b231 --- /dev/null +++ b/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/bridge/interop/InteropModuleRegistry.kt @@ -0,0 +1,49 @@ +/* + * 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. + */ + +package com.facebook.react.bridge.interop + +import com.facebook.react.bridge.JavaScriptModule +import com.facebook.react.internal.featureflags.ReactNativeFeatureFlags.enableFabricRenderer +import com.facebook.react.internal.featureflags.ReactNativeFeatureFlags.useFabricInterop + +/** + * A utility class that takes care of returning [JavaScriptModule] which are used for the Fabric + * Interop Layer. This allows us to override the returned classes once the user is invoking + * `ReactContext.getJsModule()`. + * + * Currently we only support a `RCTEventEmitter` re-implementation, being `InteropEventEmitter` but + * this class can support other re-implementation in the future. + */ +internal class InteropModuleRegistry { + private val supportedModules = mutableMapOf, Any?>() + + fun shouldReturnInteropModule(requestedModule: Class): Boolean { + return checkReactFeatureFlagsConditions() && supportedModules.containsKey(requestedModule) + } + + fun getInteropModule(requestedModule: Class): T? { + return if (checkReactFeatureFlagsConditions()) { + @Suppress("UNCHECKED_CAST") + supportedModules[requestedModule] as? T? + } else { + null + } + } + + fun registerInteropModule( + interopModuleInterface: Class, + interopModule: Any + ) { + if (checkReactFeatureFlagsConditions()) { + supportedModules[interopModuleInterface] = interopModule + } + } + + private fun checkReactFeatureFlagsConditions(): Boolean = + enableFabricRenderer() && useFabricInterop() +} diff --git a/packages/react-native/ReactAndroid/src/test/java/com/facebook/react/bridge/interop/InteropModuleRegistryTest.kt b/packages/react-native/ReactAndroid/src/test/java/com/facebook/react/bridge/interop/InteropModuleRegistryTest.kt index 63ef4bef0129..69513d722e75 100644 --- a/packages/react-native/ReactAndroid/src/test/java/com/facebook/react/bridge/interop/InteropModuleRegistryTest.kt +++ b/packages/react-native/ReactAndroid/src/test/java/com/facebook/react/bridge/interop/InteropModuleRegistryTest.kt @@ -24,7 +24,7 @@ import org.junit.Test @OptIn(UnstableReactNativeAPI::class) class InteropModuleRegistryTest { - lateinit var underTest: InteropModuleRegistry + private lateinit var underTest: InteropModuleRegistry @Before fun setup() {