pnpm monorepo中Vite构建Rollup解析JSX报错求助
问题描述
在pnpm管理的monorepo环境中,同时包含React Native项目与Vite(React Native Web)项目,构建Vite项目时出现如下Rollup报错:
error during build: RollupError: [commonjs--resolver] Expression expected in `node_modules/react-native-calendars/src/calendar/index.js` 89: }, [onSwipeLeft, onSwipeRight]); 90: const renderWeekNumber = (weekNumber) => { 91: return (<View style={style.current.dayContainer} key={`week-container-${weekNumber}`}> ^ 92: <BasicDay key={`week-${weekNumber}`} marking={weekNumberMarking.current} 93: // state='disabled'
核心问题:react-native-calendars包内用.js文件编写JSX语法,Rollup默认无法解析该类文件中的JSX,手动修改文件后缀为.jsx可解决,但文件数量较多,需更高效方案。
当前vite.config.ts关键配置见问题原文。
解决方案
方案1:修改Vite配置,让React插件转译目标包
调整@vitejs/plugin-react的范围,明确包含react-native-calendars的JS文件,同时让esbuild识别该包内JS文件为JSX格式:
// vite.config.ts import fs from 'fs'; import { defineConfig } from 'vite'; import react from '@vitejs/plugin-react'; // 其他导入... export default defineConfig({ // 其他配置... plugins: [ // 其他插件... react({ // 扩展转译范围,包含目标包的所有js/jsx/ts/tsx文件 include: ['**/*.{js,jsx,ts,tsx}', 'node_modules/react-native-calendars/**/*.js'], }), ], optimizeDeps: { // 强制预构建目标包 include: ['react-native-calendars'], esbuildOptions: { resolveExtensions: extensions, jsx: 'automatic', loader: { '.js': 'jsx', '.ts': 'tsx' }, // 添加自定义插件,精准处理react-native-calendars的js文件 plugins: [ { name: 'rn-calendars-jsx-loader', setup(build) { build.onLoad({ filter: /react-native-calendars\/.*\.js$/ }, async (args) => { const content = await fs.promises.readFile(args.path, 'utf8'); return { contents: content, loader: 'jsx' }; }); }, }, ], }, }, });
方案2:用patch-package批量修改文件后缀(持久化补丁)
通过补丁工具自动修改包内文件后缀,无需手动操作:
- 安装依赖:
pnpm add patch-package -D
- 在项目
package.json中添加postinstall脚本:
"scripts": { "postinstall": "patch-package" }
- 批量修改目标包内含JSX的
.js文件后缀:
# 在monorepo根目录执行 find node_modules/react-native-calendars -name "*.js" -exec grep -l "<" {} \; | while read file; do mv "$file" "${file%.js}.jsx"; done
- 生成补丁文件:
pnpm patch-package react-native-calendars
后续每次执行pnpm install,补丁会自动应用到react-native-calendars包。
方案3:用Rollup+Babel转译目标包
通过Rollup的Babel插件处理目标包内的JSX语法:
- 安装依赖:
pnpm add @rollup/plugin-babel @babel/preset-react -D
- 修改Vite配置:
export default defineConfig({ // 其他配置... build: { commonjsOptions: { transformMixedEsModules: true, include: /react-native-calendars/, }, rollupOptions: { plugins: [ require('@rollup/plugin-babel').babel({ include: ['node_modules/react-native-calendars/**/*.js'], presets: ['@babel/preset-react'], extensions: ['.js', '.jsx'], babelHelpers: 'bundled', }), ], }, }, });
内容的提问来源于stack exchange,提问作者Bruce Z
相关产品推荐
相关产品推荐

