React Native中TurboModules怎么调用原生方法?

Newb.玉宁 阅读 5

我按照文档配置了TurboModule,但在JS里调用时一直报undefined is not a function,是不是哪里注册错了?

我的模块叫MyLogger,在jsi::HostObject里实现了logMessage方法,也加了REACT_MODULE宏,但JS端就是找不到。

import { MyLogger } from './NativeModules';
// 或者用 requireNativeModule?
const logger = requireNativeModule('MyLogger');
logger.logMessage('test'); // 这里崩溃
我来解答 赞 1 收藏
二维码
手机扫码查看
1 条解答
❤啸天
❤啸天 Lv1
当时我也卡在这,花了好几天才搞明白。几个关键点你要注意:

首先,确保你的TurboModule在C++端实现的时候,REACT_METHOD宏别写错了,方法签名也要对,比如:

#include 
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include "MyLoggerSpecJSI.h"

namespace facebook {
namespace react {

class MyLogger : public jsi::HostObject, public MyLoggerSpecJSI {
public:
using MyLoggerSpecJSI::MyLoggerSpecJSI;

void logMessage(jsi::Runtime &rt, const std::string &message) override {
__android_log_print(ANDROID_LOG_INFO, "MyLogger", "%s", message.c_str());
}
};

} // namespace react
} // namespace facebook

extern "C" JNIEXPORT void JNICALL
Java_com_yourcompany_yourapp_YourApplication_nativeInstallMyLogger(
JNIEnv *env,
jobject thiz,
jlong jsContext) {
auto runtime = facebook::react::fromJsi((jsi::Runtime *)jsContext);
auto moduleRegistry = runtime->global().getPropertyAsObject(*runtime, "__fbBatchedBridge")
.getPropertyAsObject(*runtime, "moduleRegistry");
auto installModule = moduleRegistry.getPropertyAsFunction(*runtime, "installModule");

auto myLogger = std::make_shared();
installModule.call(
*runtime,
jsi::Value(*runtime, jsi::String::createFromUtf8(*runtime, "MyLogger")),
jsi::Value(*runtime, facebook::react::toJsi(*runtime, std::move(myLogger))));
}


注意这里的 Java_com_yourcompany_yourapp_YourApplication_nativeInstallMyLogger 方法要对应你的Android项目中的Application类。

然后在你的MainActivity或者Application类中调用这个方法安装模块:

public class YourApplication extends Application implements ReactApplication {
@Override
public void onCreate() {
super.onCreate();
SoLoader.init(this, /* native exopackage */ false);
nativeInstallMyLogger(getJavaScriptContextHolder().get());
}

private native void nativeInstallMyLogger(long jsContext);
}


最后,JS端导入的方式要注意,你上面两种方式都可以,但要确保模块名一致。你这样写应该没问题:

import { MyLogger } from 'react-native';
const logger = MyLogger;
logger.logMessage('test');


或者用require也是可以的:

const MyLogger = requireNativeComponent('MyLogger');
const logger = MyLogger;
logger.logMessage('test');


关键是确保Native模块已经正确加载并且方法签名匹配。希望这些能帮到你,踩过这个坑感觉整个人都不好了。
点赞
2026-03-22 19:30