Next.js Makes Request‑Scoped Logging Needlessly Hard

The author tries to implement request-scoped logging in Next.js and runs into hard limits: middleware can’t pass meaningful state (beyond headers), AsyncLocalStorage contexts don’t reach pages, and even custom servers don’t fix it. The required workarounds are brittle and split code across environments. By contrast, SvelteKit provides clean hooks and locals for passing data, highlighting how Next.js’s design choices and slow issue responses make it a poor developer experience.
Key Points
- Next.js middleware is highly limited: you can’t chain multiple middlewares and, in practice, only headers influence downstream routes; the default edge runtime even sends logs to the browser.
- AsyncLocalStorage context from middleware does not propagate to pages/layouts, breaking request-scoped logging and yielding null loggers.
- Workarounds (passing requestId via headers, async logger creation, and splitting middleware/server/client loggers) are cumbersome and fragile.
- Even with a custom Node server and AsyncLocalStorage, Next’s internal rendering loses the async context; meanwhile, Next uses AsyncLocalStorage internally for headers/cookies in ways developers can’t leverage.
- SvelteKit offers a superior model (handle hooks, event.locals, multiple handlers) and Next.js’s GitHub issue handling is unresponsive, compounding developer frustration.
Sentiment
The community overwhelmingly agrees with the article's frustrations. The vast majority of comments share similar negative experiences with Next.js, particularly around the App Router, middleware limitations, and vendor lock-in to Vercel. Defenders are present but heavily outnumbered, and even they tend to acknowledge the framework's significant shortcomings. The overall mood is one of accumulated frustration from developers who feel trapped by an ecosystem that was marketed as the default choice but fails at fundamental server-side tasks.
In Agreement
- Next.js middleware is fundamentally broken for real-world use — single file, no chaining, edge runtime by default, and no way to share context with page rendering
- The framework is a black box that uses AsyncLocalStorage internally but refuses to expose this capability to developers, making request-scoped patterns impossible
- Next.js's architectural constraints are designed to push developers toward Vercel's hosting platform, constituting vendor lock-in by design
- The GitHub issue tracker is a graveyard where well-documented, reproducible bugs go unanswered for years while Vercel focuses on marketing and new features
- Request-scoped logging is trivially solved in every other major framework ecosystem (Java/Spring, Python, Rails, SvelteKit) — Next.js making this impossible is a fundamental design failure
- The App Router introduced massive complexity and confusion about where code actually runs (server vs. client vs. edge), a problem the Pages Router didn't have
- React's official recommendation of Next.js as the default starting point was a mistake that pushed unnecessary complexity onto projects that don't need it
Opposed
- The author's problems stem from misunderstanding Next.js's middleware design — it's meant as a lightweight hook, not as traditional Express-style middleware
- Next.js works well when you use it within its intended design and don't fight the framework's conventions
- Next.js is fine for frontend-only or simple fullstack use cases — the issues only emerge when trying to use it as a general-purpose backend framework
- Every framework has tradeoffs and rough edges; Next.js remains dominant for a reason despite its flaws
- The fact that the blog post criticizing Next.js was itself built on Next.js (via leaflet.pub on Vercel) demonstrates that the framework does work