Skip to content

Commit d5b9e79

Browse files
cipolleschifabriziocucci
authored andcommitted
Be less strict with method parsing of TurboModule Interop Layer (#49072)
Summary: Pull Request resolved: #49072 We have instance of apps crashing when enabling the New Architecture because of the TurboModule interop layer. What's happening is that when the module is loaded, the TM Interop Layer tries to parse the method definition to expose them in JS. However, for some libraries in the Legacy Architecture, it is possible to define a method in Objective-C and to define a different signature in Swift. For example, the [`RNBluetoothClassic` library](https://github.com/kenjdavidson/react-native-bluetooth-classic) defines a selector in objective-c which [has the signature](https://github.com/kenjdavidson/react-native-bluetooth-classic/blob/main/ios/RNBluetoothClassic.m#L134-L136) ``` RCT_EXTERN_METHOD(available: (NSString *)deviceId resolver: (RCTPromiseResolveBlock)resolve rejecter: (RCTPromiseRejectBlock)reject) ``` And the method is inmplemented in Swift with [the signature](https://github.com/kenjdavidson/react-native-bluetooth-classic/blob/main/ios/RNBluetoothClassic.swift#L502-L505): ``` func availableFromDevice( _ deviceId: String, resolver resolve: RCTPromiseResolveBlock, rejecter reject: RCTPromiseRejectBlock ) ``` When the TurboModule interop layer tries to parse the method, it receives the `accept:resolver:rejecter:` signature, but that signature is not actually defined in as a method in the module instance, and it crashes. This crash was not happening in the Old Architecture, which was handling this case gracefully. Notice that the specific method from the example is not working in the Old Architecture either. However, the app is not crashing in the old architecture. This change adds the same graceful behaviors plus it adds a warning in development to notify the developer about which methods couldn't be found in the interface. Fixes: - #47587 - #48065 ## Changelog: [iOS][Fixed] - Avoid crashing the app when the InteropLayer can't find some methods in the native implementation. Reviewed By: javache Differential Revision: D68901734 fbshipit-source-id: 844d1bf29423d5c601b583540e86d57dfffd1428
1 parent 5f1aeff commit d5b9e79

File tree

1 file changed

+9
-0
lines changed

1 file changed

+9
-0
lines changed

packages/react-native/ReactCommon/react/nativemodule/core/platform/ios/ReactCommon/RCTInteropTurboModule.mm

+9
Original file line numberDiff line numberDiff line change
@@ -123,6 +123,15 @@
123123
NSArray<RCTMethodArgument *> *arguments;
124124
SEL objCMethodSelector = NSSelectorFromString(RCTParseMethodSignature(methodInfo->objcName, &arguments));
125125
NSMethodSignature *objCMethodSignature = [moduleClass instanceMethodSignatureForSelector:objCMethodSelector];
126+
if (objCMethodSignature == nullptr) {
127+
RCTLogWarn(
128+
@"The objective-c `%s` method signature for the JS method `%@` can not be found in the ObjecitveC definition of the %s module.\nThe `%@` JS method will not be available.",
129+
methodInfo->objcName,
130+
jsMethodName,
131+
moduleName.c_str(),
132+
jsMethodName);
133+
continue;
134+
}
126135
std::string objCMethodReturnType = [objCMethodSignature methodReturnType];
127136

128137
if (objCMethodSignature.numberOfArguments - 2 != [arguments count]) {

0 commit comments

Comments
 (0)