next.js
next.js copied to clipboard
allow importing "server-only" modules in `next.config.js`
Link to the code that reproduces this issue
https://github.com/stefanprobst/issue-next-config-server-import
To Reproduce
- clone https://github.com/stefanprobst/issue-next-config-server-import and run
pnpm install pnpm run dev- see error message:
⨯ Failed to load next.config.js, see more info here https://nextjs.org/docs/messages/next-config-error
> Build error occurred
Error: This module cannot be imported from a Client Component module. It should only be used from a Server Component.
Current vs. Expected behavior
i am trying to import a module which has import "server-only"; into next.config.js and get the following error:
⨯ Failed to load next.config.js, see more info here https://nextjs.org/docs/messages/next-config-error
> Build error occurred
Error: This module cannot be imported from a Client Component module. It should only be used from a Server Component.
i had assumed that next.config.js would not be read client side.
i also checked whether next.config.js is actually read client-side by adding the following code in next.config.js (and everything still worked, so i guess importing from server-only modules should be ok):
if (typeof document !== "undefined") {
throw new Error("Reading next.config.js on the client.");
}
Provide environment information
Operating System:
Platform: linux
Arch: x64
Version: #202403151937 SMP PREEMPT_DYNAMIC Fri Mar 15 19:52:22 UTC 2024
Available memory (MB): 31401
Available CPU cores: 16
Binaries:
Node: 20.12.2
npm: 10.5.0
Yarn: 1.22.19
pnpm: 9.0.6
Relevant Packages:
next: 14.3.0-canary.57 // Latest available version is detected (14.3.0-canary.57).
eslint-config-next: N/A
react: 18.3.1
react-dom: 18.3.1
typescript: 5.4.5
Next.js Config:
output: N/A
Which area(s) are affected? (Select all that apply)
Module Resolution
Which stage(s) are affected? (Select all that apply)
next dev (local)
Additional context
also see this discussion: https://github.com/vercel/next.js/discussions/65605#discussioncomment-9393115
I would also want this.
I'm migrating from pages to app directory and my pages depend on publicRuntimeConfig. For my publicRuntimeConfig to work, I'm importing ~/server/env.js which I would very much like to have import 'server-only' in now that the boundary between server and client is more fuzzy
@huozhi could you clarify whether this is indeed an issue, or if this is intended behavior? thank you!
ok so the docs state:
next.config.js is a regular Node.js module ... It gets used by the Next.js server and build phases, and it's not included in the browser build.
A slightly hacky workaround I'm using for now:
try {
require("server-only");
} catch (err) {
if (err && typeof err === "object" && "code" in err && err.code === "MODULE_NOT_FOUND") {
} else {
throw err;
}
}
But yea, it would be nice if it just worked.
Edit: My workaround only works if server-only is not explicitly included in the package.json.
+1 for this feature, I want to mark my server configuration as server only, but I want to check it on build.
+1 - I am trying to import a "server only" file to validate server environment variables in next.config so that it validates at build time
server-only actually means react-server-only, which when the environment will pick up react-server export condition of an export from a package, which is mostly designed for RSC. next.config.js is not bundled and it's loading modules through the default node.js export order, where react-server condition is not preferred. Hence it's actually just the default runtime, not "server-only", more like not "react server" only
thanks for the explanation @huozhi! i guess this is working as intended then.
@huozhi @stefanprobst - Is there any workaround? Is it possible to do anything so that "server-only" doesn't trigger when imported from the config file?
This closed issue has been automatically locked because it had no new activity for 2 weeks. If you are running into a similar issue, please create a new issue with the steps to reproduce. Thank you.