You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React Native Monorepo结构下使用Expo-Router打包成功后运行出现Hermes引擎相关TypeError问题求助

React Native Monorepo结构下使用Expo-Router打包成功后运行出现Hermes引擎相关TypeError问题求助

大家好,我目前在Monorepo结构下用React Native + Expo-Router开发应用,遇到了打包成功但App运行报错的棘手问题,想请各位帮忙分析下原因。

问题经过

一开始打包Android时,我碰到了Expo-Router的路径错误:

ERROR node_modules/expo-router/_ctx.android.js:Invalid call at line 2: process.env.EXPO_ROUTER_APP_ROOT First argument of require.context should be a string denoting the directory to require.

按照官方文档指引,我在index.js中添加了根组件注册代码,成功解决了打包问题,Android端终于bundle成功:

import { registerRootComponent } from 'expo';
import { ExpoRoot } from 'expo-router';

export function App() {
  const ctx = require.context('./app');
  return <ExpoRoot context={ctx} />;
}

try {
  registerRootComponent(App);
} catch (e) {
  console.error("App registry failed:", e);
}

但当我打开App时,出现了一连串Hermes引擎相关的报错:

ERROR ExceptionsManager should be set up after React DevTools to avoid console.error arguments mutation
ERROR TypeError: property is not writable, js engine: hermes
ERROR TypeError: Cannot read property 'default' of undefined, js engine: hermes
ERROR TypeError: property is not writable, js engine: hermes
ERROR TypeError: Cannot read property 'default' of undefined, js engine: hermes

我的配置文件

下面是我当前项目的核心配置,供大家参考:

Babel.config.js

module.exports = function (api) {
  api.cache(true);
  process.env.EXPO_ROUTER_APP_ROOT = "./app";
  return {
    presets: ['babel-preset-expo'],
    plugins: ['expo-router/babel'],
  };
};

metro.config.cjs

const { getDefaultConfig } = require('@expo/metro-config');
const path = require('path');

const projectRoot = __dirname;
const monorepoRoot = path.resolve(projectRoot, '../..');

// 共享的Monorepo包路径
const monorepoPackages = {
  '@trungthao/domain': path.resolve(monorepoRoot, 'Packages/Domain'),
};

// Metro基础配置
const config = getDefaultConfig(projectRoot);

// 1. 监听本地与共享包目录
config.watchFolders = [projectRoot, ...Object.values(monorepoPackages)];

// 2. 正确处理软链接
config.resolver.extraNodeModules = new Proxy({}, {
  get: (_, name) => 
    name in monorepoPackages 
      ? monorepoPackages[name] 
      : path.join(monorepoRoot, 'node_modules', name),
});

// 3. 模块解析优先级
config.resolver.nodeModulesPaths = [
  path.resolve(projectRoot, 'node_modules'),
  path.resolve(monorepoRoot, 'node_modules'),
];

// 4. 显式指定入口文件
config.entryFile = 'index.tsx';

module.exports = config;

package.json

{
  "name": "mobileapp",
  "version": "1.0.0",
  "description": "",
  "main": "index.js",
  "scripts": {
    "start": "expo start",
    "android": "expo run:android",
    "ios": "expo run:ios",
    "web": "expo start --web",
    "build": "expo export",
    "test": "jest",
    "eas-build-post-install": "cd ../../Packages/Domain && npm install && npm run build"
  },
  "keywords": [],
  "author": "",
  "license": "ISC",
  "type": "module",
  "dependencies": {
    "@expo/metro-config": "^0.20.15",
    "@expo/vector-icons": "^14.1.0",
    "@gorhom/bottom-sheet": "^5.1.4",
    "@ptomasroos/react-native-multi-slider": "^2.2.2",
    "@react-native-async-storage/async-storage": "2.1.2",
    "@react-native-community/datetimepicker": "^8.4.1",
    "@react-navigation/bottom-tabs": "^7.2.0",
    "@react-navigation/native": "^7.0.14",
    "@reduxjs/toolkit": "^2.7.0",
    "@trungthao/domain": "*",
    "bcryptjs": "^3.0.2",
    "cors": "^2.8.5",
    "dotenv": "^16.4.1",
    "expo": "53.0.13",
    "expo-blur": "~14.1.5",
    "expo-constants": "~17.1.6",
    "expo-dev-client": "~5.2.2",
    "expo-device": "~7.1.4",
    "expo-document-picker": "~13.1.6",
    "expo-file-system": "^18.1.10",
    "expo-font": "~13.3.1",
    "expo-haptics": "~14.1.4",
    "expo-image": "~2.2.1",
    "expo-image-manipulator": "^13.1.7",
    "expo-image-picker": "^16.1.4",
    "expo-linear-gradient": "~14.1.5",
    "expo-linking": "~7.1.4",
    "expo-media-library": "^17.1.7",
    "expo-notifications": "~0.31.3",
    "expo-router": "~5.1.1",
    "expo-screen-orientation": "~8.1.7",
    "expo-splash-screen": "~0.30.9",
    "expo-status-bar": "~2.2.3",
    "expo-symbols": "~0.4.5",
    "expo-system-ui": "~5.0.9",
    "expo-web-browser": "~13.0.3"
  }
}

我的猜测

目前我怀疑几个方向:

  1. Monorepo共享包@trungthao/domain的导出或引用有问题,导致Cannot read property 'default' of undefined
  2. Expo-Router在Monorepo场景下的配置存在遗漏,和Hermes引擎的兼容性问题
  3. index.js中的require.context用法是否和Monorepo的模块解析冲突?

有没有朋友遇到过类似的问题,或者能帮我排查下可能的原因?感谢大家的帮助!

内容来源于stack exchange

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.07 11:08:05