Turbopack breaks when parsing react-native code
Link to the code that reproduces this issue
https://github.com/xLucaH/react-native-starter
To Reproduce
- Clone the application above
- Run
pnpm devand openlocalhost:3000, see that it's working - Change
/apps/web/package.jsonto have"dev": "next dev --turbo" - Run
pnpm devagain and see the error
Current vs. Expected behavior
We get an error:
## Error Type
Build Error
## Error Message
Parsing ecmascript source code failed
## Build Output
./node_modules/react-native/Libraries/Utilities/codegenNativeComponent.js:13:13
Parsing ecmascript source code failed
11 | // TODO: move this file to shims/ReactNative (requires React update and sync)
12 |
> 13 | import type {HostComponent} from '../../src/private/types/HostComponent';
| ^
14 |
15 | import requireNativeComponent from '../../Libraries/ReactNative/requireNativeComponent';
16 | import UIManager from '../ReactNative/UIManager';
Expected ',', got '{'
Import traces:
Client Component Browser:
./node_modules/react-native/Libraries/Utilities/codegenNativeComponent.js [Client Component Browser]
./node_modules/react-native-safe-area-context/lib/module/specs/NativeSafeAreaView.js [Client Component Browser]
./node_modules/react-native-safe-area-context/lib/module/SafeAreaView.js [Client Component Browser]
./node_modules/react-native-safe-area-context/lib/module/index.js [Client Component Browser]
./node_modules/react-native-css-interop/dist/runtime/components.js [Client Component Browser]
./node_modules/react-native-css-interop/dist/runtime/wrap-jsx.js [Client Component Browser]
./node_modules/react-native-css-interop/dist/runtime/jsx-dev-runtime.js [Client Component Browser]
./node_modules/nativewind/jsx-dev-runtime/index.js [Client Component Browser]
./apps/web/src/app/registry.tsx [Client Component Browser]
./apps/web/src/app/registry.tsx [Server Component]
./apps/web/src/app/layout.tsx [Server Component]
Client Component SSR:
./node_modules/react-native/Libraries/Utilities/codegenNativeComponent.js [Client Component SSR]
./node_modules/react-native-safe-area-context/lib/module/specs/NativeSafeAreaView.js [Client Component SSR]
./node_modules/react-native-safe-area-context/lib/module/SafeAreaView.js [Client Component SSR]
./node_modules/react-native-safe-area-context/lib/module/index.js [Client Component SSR]
./node_modules/react-native-css-interop/dist/runtime/components.js [Client Component SSR]
./node_modules/react-native-css-interop/dist/runtime/wrap-jsx.js [Client Component SSR]
./node_modules/react-native-css-interop/dist/runtime/jsx-dev-runtime.js [Client Component SSR]
./node_modules/nativewind/jsx-dev-runtime/index.js [Client Component SSR]
./apps/web/src/app/registry.tsx [Client Component SSR]
./apps/web/src/app/registry.tsx [Server Component]
./apps/web/src/app/layout.tsx [Server Component]
Next.js version: 15.5.0 (Turbopack)
I'd expect that this would work.
Provide environment information
Operating System:
Platform: linux
Arch: x64
Version: #202510191616~1761932270~24.04~b3a306c SMP PREEMPT_DYNAMIC Fri O
Available memory (MB): 15659
Available CPU cores: 20
Binaries:
Node: 22.20.0
npm: 10.9.3
Yarn: N/A
pnpm: 10.15.0
Relevant Packages:
next: 16.1.0-canary.12 // Latest available version is detected (16.1.0-canary.12).
eslint-config-next: 15.5.0
react: 19.1.0
react-dom: 19.1.0
typescript: 5.9.3
Next.js Config:
output: N/A
Which area(s) are affected? (Select all that apply)
Turbopack
Which stage(s) are affected? (Select all that apply)
next dev (local), next build (local), next start (local), Vercel (Deployed)
Additional context
I've tried this on Next.js 15.5 and the latest canary as well. Seems like this might be an issue with parsing Flow syntax?
This might seem niche, but it's actually pretty common to develop apps with code shared between Next.js and React Native. Allowing Turbopack would be really helpful.
This is failing because it's trying to parse Flow syntax. We generally assume that code in node_modules is stripped of types and is valid JS.
https://github.com/facebook/react-native/blob/5bb3a6d68db113d49528848df8704c5adeb1eba8/packages/react-native/Libraries/Utilities/codegenNativeComponent.js#L7
The correct thing would be for react-native to strip the types before publishing, but you could configure a custom babel-loader to strip the types: https://nextjs.org/docs/app/api-reference/config/next-config-js/turbopack#configuring-webpack-loaders
Note that you cannot use the built-in babel-loader functionality that Next.js ships with for this, because we don't run the loader over code in node_modules. For performance reasons, you'll want to configure the loader so that it only runs over node_modules/**/react-native/**/*.js.
Given that you probably don't actually want to import the real react-native code from within a next.js app, you could try using a resolveAlias config to replace things with stub modules: https://nextjs.org/docs/app/api-reference/config/next-config-js/turbopack#resolving-aliases
The configuration of resolveAlias is a little more limited and less flexible than the configuration of webpack loaders (we could make this better by porting over the condition field), but it should also be more performant.
react-native doesn't work in a web context anyway. You want react-native-web.
See this config for example:
https://github.com/nandorojo/solito/blob/2cc9f5e3a24e93ce974312bbaf95d61722e66342/develop/appdir/next.config.js#L37
Thanks for the pointers! I'm still getting unfortunately getting errors after adding the turbopack config from Solito to the Next config. I'm not working on the same project anymore so don't have time to debug, but see https://github.com/bgub/rn-next-repro.git for an example.