Next.js "Cannot read properties of undefined (reading 'length')" in installChunk: two processes share .next
I opened the dashboard of my Next.js app and got a 500 error:
GET /app/dashboard 500 in 285ms
⨯ TypeError: Cannot read properties of undefined (reading 'length')
at <unknown> (.next/server/app/app/accounts/page.js:685:47)
at Object.<anonymous> (.next/server/app/app/accounts/page.js:688:3) {
page: '/app/accounts'
}
GET /app/accounts 500 in 278ms
If the stack points into generated .next/server/.../page.js and the full trace ends in installChunk in webpack-runtime.js, your code is fine. Another Next process has written into the .next directory your dev server is reading from.
The setup #
- Next.js 15.5 with webpack in dev, in a pnpm monorepo (the app lives in
apps/web) pnpm devrunning in my terminal on port 3000- A coding agent working in the same checkout, which checks its work with
pnpm build
What went wrong #
I asked the agent to fix the 500. It did what anyone would do with reading 'length': it grepped the app for .length. The accounts page didn’t touch a collection at all, so the agent followed the authenticated layout into the auth code and suspected an import there. Then it opened the generated page.js at line 685 and found webpack glue, not application code.
To reproduce, the agent ran pnpm build, which succeeded, and then started its own next dev -p 3001 next to mine. The first request to /app/accounts returned 200. After a request to the dashboard, both routes returned 500, and this time the error page carried the whole stack:
TypeError: Cannot read properties of undefined (reading 'length')
at installChunk (apps/web/.next/server/webpack-runtime.js:249:41)
at __webpack_require__.f.require (apps/web/.next/server/webpack-runtime.js:259:15)
...
at apps/web/.next/server/app/app/dashboard/page.js:718:47
Line 249 is in webpack’s chunk loader:
var installChunk = (chunk) => {
var moreModules = chunk.modules, chunkIds = chunk.ids, runtime = chunk.runtime;
// ...
for(var i = 0; i < chunkIds.length; i++)
installedChunks[chunkIds[i]] = 1;
};
chunk is whatever require("./" + chunkFile) returned. chunk.ids was undefined, so the file on disk was not the chunk this runtime expected. A ps showed why: two next-server processes, mine on 3000 and the agent’s on 3001, both compiling into apps/web/.next. On top of that, the agent’s next build had written its production output into the same directory a few minutes earlier.
Both of the usual ways to reproduce a bug, a fresh build and a second server, are ways to cause this one. Before you reproduce, look for other Next processes on the checkout:
ps -axo pid,ppid,command | grep '[n]ext-server'
Fix #
Give next dev its own output directory in next.config.mjs:
export default {
// `next dev` and `next build` generate incompatible webpack chunk graphs.
// Keep their output separate so a build cannot break a running dev server.
distDir: process.env.NODE_ENV === "development" ? ".next-dev" : ".next",
};
Ignore it in .gitignore:
.next/
.next-dev/
Add its generated types to tsconfig.json, next to the .next ones:
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts", ".next-dev/types/**/*.ts"]
The running dev server picked up the config change and rebuilt into .next-dev. From then on, next build writes to .next and the dev server never reads it.
To recover without the config change, stop every Next process except one, delete .next and restart pnpm dev.
If you’re on Next.js 16, you already have this: next dev writes to .next/dev, so dev and build can run concurrently
.
The follow-on trap: next-env.d.ts #
Next rewrites next-env.d.ts on every dev start and every build, and the file names the types of whichever directory ran last:
/// <reference path="./.next-dev/types/routes.d.ts" />
After every next build, it says ./.next/types/routes.d.ts instead. The file was tracked, so it showed up as modified in later sessions, and the agents kept “fixing” it with git show HEAD:apps/web/next-env.d.ts > apps/web/next-env.d.ts. Do what the .gitignore from create-next-app does and ignore the file:
echo 'next-env.d.ts' >> apps/web/.gitignore
git rm --cached apps/web/next-env.d.ts
Why #
next dev and next build both default to .next in Next.js 15, and they write different chunk graphs into it. A second next dev is no better: two webpack compilers write into one directory, and neither knows about the other. The runtime that is already loaded require()s a chunk by the name from its own graph, gets a file the other compilation wrote, and fails at chunk.ids.length. The error says length, so you go looking for an array in your code.
Coding agents check their work with next build, usually while your dev server is still running, so you’ll hit this more often than you’d think.
Takeaway #
An error from inside installChunk points at the build directory, so look for a second Next process before you read your own code. Never let two Next processes share a distDir.
If an agent or a script runs next build in the checkout where your dev server runs, give dev its own distDir today.