Hacker Newsnew | past | comments | ask | show | jobs | submitlogin
Next.js App Router Update (nextjs.org)
59 points by feross on June 22, 2023 | hide | past | favorite | 89 comments


I've recently started to get burnt out by Next.js. Most of its benefits stems from its SSR capabilities. However, that is also the part that is most buggy and keeps changing. It keeps improving but it just isn't there yet.

Perhaps it's because I'm leaning my focus into business now. But it's so much faster to build landing pages using old stuff like wordpress. Sure it has its downsides but it brings so much to the table. And there's so much plugins to do everything you need. Caching? 1 click install and done. SEO? Easy. Admin panel? Built in.

And say you're building a SaaS. The internal app could be whatever you want it to be. Since it's internal, there's no need to worry about SEO. At that point, I'd rather use SPA to avoid all the issues Next.js brings.

Though that's not to say Next.js is all bad. I just think it's not there yet and it may be a while until it becomes stable.


Lots of negativity here. I don’t share the sentiment. I have ported one project over to the app router months ago when it was still in beta with zero problems and another one is in the works using server actions and drizzle-orm to get end to end type safety. I think it’s a blast. For those complaining about the feature set growing: I think this is just a question of use-case. At my current gig we are using pretty much everything next has to offer for a fairly sophisticated eCommerce site. If your app has thousands of pages (like product pages) with integration into a dozen micro services, auth, large images everywhere, redirects everywhere for seo purposes, middleware for various purposes, i18n and needs SSG for seo and perf reasons then next offers pretty well thought out solutions for all of that.

I can understand the performance argument but most of that is being worked on and the next team has already shipped lots of improvements in the past. But maybe the things I worked on haven’t reached a scale yet where these things become a bottleneck.


Yeah overall I like the new app router a lot. The pages structure was a mess.

It definitely could be better. They're making a pathing mess with eg. parallel routes but it's not /that/ big of a deal all in all. The problem being that when you rely on file paths for routing, you then end up having to build in all kinds of hacks and conventions in the file paths, which are just... not designed for that, they're just keys to files.

But the core of the structure and architecture is sound.


I just looked into the Server Actions documentation. Why is there a 'use server' inside the action if it's already running on the server? What happens if this is omitted? Why is all of this stuff so opaque?

https://nextjs.org/docs/app/building-your-application/data-f...


I think, if I'm recalling it correctly, that the component that is defining it in the docs can be either client or server and by marking the functiom as server only, Next knows to do magic.


Next may know that but developers sure won't.


This kind of noodley bundling opt-out is also extremely dangerous from a security perspective. I expect there are a lot of Next.js apps leaking code and possibly secrets that should only be available on the server.


Thanks for sharing your good sentiment here.

I would be happy to talk about NextJS and LLM's and AI if you're up for it.

Leaving my email on my profile for some days.


Anyone sharing the disappointment with NextJS, please have a second look at https://www.meteor.com/ again. It is much more powerful in terms of backend/frontend communication and reactivity, and even though there was a huge downturn some years ago, its picking up steam again. Importantly: it has been around for roughly a decade now and in most cases "just works", and you can even pick the frontend lib you like (react/vue/svelte/...) or swap it later on, so no _hard_ coupling to react. I blogged about it a while ago (https://anonyfox.com/blog/the-renaissance-of-meteor-js/) and things are getting even better now. There are still rough edges, but central points like SSR that "just works" with "useTracker" is there.


Also have a look at https://vite-plugin-ssr.com/ (author here).

VPS is slightly lower level which gives you a lot more control: integrate with your existing Node.js backend (use any backend framework you want), deploy anywhere, use any React alternative (Solid, Preact, ...) and any data fetching tool (e.g. Relay can't really be used with Next.js).

The flip side is that you've to write a little bit more glue code. Although this will be alleviated by a lot with projects such as Bati[0], Stem[1], and vike-react (see Vike Rebranding[2]).

VPS also cares a ton about details, such as hooks for full control over i18n (use any i18n strategy you want), better Base URL support (VPS supports setting a different base for your server and your CDN), automatic deploy synchronisation, domain-driven file structure, polished and helpful error messages (especially the next upcoming release), ...

Detailed comparison with Next.js: [3].

If you run into any blocker then it's quickly fixed (or at least a workaround is proposed).

It supports not only SSR and pre-rendering, but also SPA in case you don't need SSR. It's going to support RSC but doesn't yet (RSC isn't ready for production).

Because it's lower level and because it's decoupled from React everything is designed in an agnostic way and with meticulous care. In other words: vite-plugin-ssr is becoming a robust foundation. There are breaking changes coming for the v1 release but beyond that chances are that there won't be any breaking changes for years in a row.

In a nutshell: vite-plugin-ssr takes care of the frontend and only the frontend. You keep control over your architecture. (Whereas frameworks tend to put themselves right in the middle of your architecture restricting you in fundamental ways.)

Last but not least: it's powered by Vite which means blazing fast HMR.

[0] https://batijs.github.io

[1] https://stemjs.com/

[2] https://github.com/brillout/vite-plugin-ssr/issues/736

[3] https://vite-plugin-ssr.com/nextjs-comparison


As a long term user of old school server side frameworks like PHP I very much "got" what the app router is trying to do once I used it, being able to reach into your database from any component without having to build an API layer is incredibly productive. It feels refreshingly old school and new school at the same time. My guess is the majority of the people that don't like the app router are just very used to the modern SPA only way of building websites and will come around over time. I think the idea of server components themselves are incredibly solid and expect to see other frameworks adopt them as well.


I don't get it.

Why not use simple .htaccess to map URLs to folders/files like always? Then, if you simply must use a JS framework like React...run it on those corresponding pages. Why use yet another framework (Next) on top of this to handle such a simple thing?


I think what you are getting at is what the new nextjs is. Everything is just plain server rendered HTML by default and you opt into client side react on a per-subtree basis depending on if you need it or not.

Some other neat bonuses are:

- Page transitions still use client side routing so it still feels fast like a SPA, and it automatically preserves state on your outer layouts during page changes.

- And something I find mind blowingly impressive is you can refresh the server rendered HTML at any point while the user is on the page while still preserving all of their client side state and scroll position etc. A simple call to `router.refresh()` is all you need to do that, something that would have taken a good amount of API code and shoving stuff into some state management library etc to do before.


I’m not a next.js or react fan at all, but “like always” is a weird thing to say about a feature that is Apache only.

While Apache was wildly popular htaccess files and cgi/fcgi adapters for php, Perl and such were everywhere. These days they’ve fallen out of favor and every cloud provider has their own version of this that you can use.

But let’s not pretend this is the way things have always been done, in my career pre-cloud I’ve worked with Apache and nginx, but also with Java servers (tomcat etc), phusion, IIS and occasionally custom app servers that would speak http.


I worked on a couple of Next.js projects and all of them turned into a code mess. I have more than a year of experience with Next.js as a senior developer and I still don't know what this frameworks was built for? Is it for a blog post or a full blown app? It started as a framework for a simple blog, but now it turned into this Frankenstein monster and I despise working with it. This is all the sad side effect of JavaScript ecosystem not having a good backend framework like Ruby on Rails or Django. It's a shit show.


I think this has more todo with ad-hoc programing without any guide lines than something inherent to Next.js. If you adopt a basic folder structure to place models, interfaces, routes and what not in, I don't see how things can become super messy. Using Typescript can help to more easily navigate the code base.


I gave up on Next.js because of it's architecture. It does not support normal authentication use cases via cookies eg. include the logged in user's name. Next.js wants to prerender a page such that any user can be served it. This means that your first paint will always be incomplete since you have to fill in all the user specific stuff client side.

I ended up migrating to Remix and my application was easy to build how I wanted with cookies. Next.js API for working with cookies wasn't that good either.

Unfortunately, this update did not include anything to address this. Next.js seems fine to use if you are making a landing page or some site which does not require authentication, but I wouldn't use it for anything complex.


Agree, it's like they made no effort to make hydration easier. Even the router doesn't have the route info on the first render on the client, I had to pass it with getServerSideProps, that's ridiculous.

If you have to re-engineer all your code to avoid content shift, why bother using a mega-framework like Next in the first place? Also the point of SSR and hydration is to improve performance and page loads, if you have a ton of work to do again on the client that's very small actual performance gains, but that's not so much of a surprise considering Next is one of the heaviest frameworks out there (in bundle size)


You can use getServerSideProps to look at the cookies before rendering the page for a user.

It’s slightly annoying though since you can’t use both getServerSideProps and getStaticProps on the same page.


Except getServerSideProps is no longer used in Next 13 and actually you have no simple access to the request object anymore. Have to write middleware for everything, it is extremely frustrating


To clarify -- using getServerSideProps works for routes defined in the pages/ directory in Next 13, but not for routes defined in the app/ directory. Both pages and app are still fully supported in Next 13. See https://nextjs.org/docs/app/building-your-application/routin...


You can just call the `cookies()` or `headers()` function in every server component in the app router?


Yeah which honestly I don't mind the middleware approach for authentication although the route matching is pretty bad for fine grain control.

However another thing is the middleware is all through the edge runtime. So things like regular postgres drivers don't work (although I did hear that Cloudflare workers added TCP so maybe that's coming).

I will say Planetscale and the hottest db as a service platforms all seem to have an edge adapter to allow for this but your SOL otherwise.


Yes, I tried making a middleware for auth, but it just was not working for me. I think I had trouble passing along information to the actual page or something. I also was unable to have my login page handle authentication to set the cookie so I had to do go and make an API for it. I eventually cut my losses and gave up since it felt like my app was going against the grain.


> Except getServerSideProps is no longer used in Next 13

Yes it is?


Ah, I see. That’s very annoying.


Fwiw, iron session is working ok on client and ssr for me.


I have found that it is pretty difficult to find what I'm looking for when searching for articles/issues that relate in any way to the Next router. "App router" and "pages router" were two of the most ungooglable and generic name they could have chosen. Suddenly it is much more difficult to find what I'm looking for in the ecosystem.


Sorry about this. I work on the documentation (author of the post). Are you talking about searching through the docs or searching through GitHub? ARe there specific things you've searched for you couldn't find?


It has been primarily related to web search and Github. It has been a month or two since I last tried the Next.js app router and I don't remember specifics, but I do recall that my workflow often involved searching for an issue, article, or guide related to how to accomplish something or fix something in relation to the router, but with the distinction between routing mechanisms being represented by these relatively generic nouns (app/pages), I found it difficult/cumbersome to identify if the information I was looking at was pertinent to the routing mechanism I was using. I wouldn't be surprised if the situation has improved by now.

I'd also like to mention that I regret my uncharitable phrasing in my original comment "…the most ungooglable and generic name they could have chosen…". While I do think more specific names might have helped in some ways, I can appreciate the difficulty in coming up with names for this kind of thing.


Naming things is hard. On the one hand, I prefer descriptive names like app router. On the other, idiosyncratic names like, idk, Pinecone are more googleable but opaque and hard to remember sometimes.

I used the CSS toolkit called Less and that name took the worst out of each hand. That was just terrible re: searching for things.


Agreed, nextJS feels incredibly overloaded with lots of terms that seem to conflate.

I tried to use the new app router, but it felt infuriatingly opaque to me, so I just went back to pages. Fortunately you can use the newest nextJS v13 and still have access to the old Pages system.


So, are we all just ignoring the fact that the new app router is twice as slow, compared to the old pages router? [0][1]

Yet it'll replace pages router in the near future, seems like a risky situation to be in as a pages router fan.

The folder structure is also very 'angular' and opinionated. It has started to disappoint me that Next.js is becoming too opinionated as time goes on and the 'new' things are nothing but worse in performance and DX. The pages folder structure was awesome, easy to understand and manage. Now it's all just 10s of page.tsx files in your editor.

I used to love Next.js, I still do but I'm not sure if I will in the near future.

[0] https://m.youtube.com/watch?v=3Q2q2gs0nAI

[1] https://m.youtube.com/watch?v=hr_y1hIdZHs&t=644s


Not only is it slower compared to pages, but we've found that upgrading Next dramatically slows down our app even if we don't have an app folder at all.


I’ve recently started working with NextJs and absolutely loving it so far.

However, with adopting the App Router there is a big looming question - what happens with frontend state/query management libraries like react-query/trpc?

So far, I’ve seen unergonomic solutions that require the developer to manually hydrate the frontend. Hopefully, over the next few months we discover a solution that “just works”, so we can widely adopt RSC.


You can continue to use state management libraries that take advantage of React hooks or other client-side logic inside of client components. Alternatively, you can move state management entirely to the server. That could be state in your database, URL state, or something else.


Hey Lee! Thanks so much for responding.

What's not clear to me is where do the providers go (ReduxProvider, ReactQueryProvider etc)?

Can they be instantiated up tree in a server component somewhere? And if that's the case, what data do they hold when on the server and what happens a client component tries to interact with the provider?

Or should I render as much as possible via RSC and put the providers in the first client component in the tree?

I've been trying to keep tabs on the GitHub issues and Discord that discuss this, but I have to admit, it's a bit over my head. The best resource I've found so far to understand how libraries are adapting is from Apollo's RFC here: https://github.com/apollographql/apollo-client-nextjs/blob/p...


Sorry for the late reply, but we have docs here! https://nextjs.org/docs/getting-started/react-essentials#con...


Currently, standalone Next.js apps using App Router consume a lot of memory and leak memory over time (issue #49929 has been open for over a month). I would greatly appreciate it if the Next.js team could investigate this matter (see my comment here: https://github.com/vercel/next.js/issues/49929#issuecomment-...). As it stands, this issue is preventing me from adopting App Router for new projects.


The new docs are extremely annoying; if you're still running a legacy app, sometimes you get put into a doc for a feature you think exists, but then you realize it's not for the right version you're running.

Also the new app routers are very confusing. There are concepts of a layout, template, page, etc. While it's nice to have server rendering at this level, it's difficult to understand what is bubbling which direction, and when to use a layout vs a template. Sometimes after building something one way (eg using layout), you realize you actually need to build it using the other in order for specific features to work.

Old Next was great and simple- new Next has become increasingly frustrating and not so easy to adopt.


Apps using the Pages Router aren't legacy, it's totally fine and encouraged to continue using it. We'll continue to support in far into the future and also be adding some new features there, too.

Where are you landing into the docs from, Google? We try to add version history notes at the bottom of docs pages, but maybe we should place these at the top. Open to feedback.


Just keep the old version's docs and have a version select drop down.

I don't want to trawl through what is essentially a changelog, I want to browse/search the docs for the version I am using.


Pressing command+k, attempting to find a solution to an issue- but the solution is for app routes not pages route.

Having them separate was better for documentation satisfaction.


This new routing approach with fetching data everywhere will end up like old PHP mess and then they will discover controllers again :)

I’ve tried to make it work for SPA development but it doesn’t work in that scenario well as all recent data fetching libs were using hooks which you can’t use in async functions. Seem like people aren’t sure how to best solve it now.


It's crazy to me that their docs aren't versioned. Almost forces you to be constantly upgrading to the bleeding edge.


What are the viable alternatives for those who don't care about the API routes but still want some level of pre-rendering / SSR? Staying in the React ecosystem that is.

Remix is always touted as the alternative but it seems like a whole new approach to learn and it's own strong opinions.

I've been using Next for 3+ years but I don't feel confident to start a new project today. Do I go to the dying page router? Or trail blaze with the app router with all the teething issues and issues everyone's encountering (myself included).


To be honest I think Next with the pages router is still the best option you have today.

I'm not convinced the server components experiment is going to work in the end. They might even end up abandoning it.


API routes are nothing new, and not a big part of the new App router (also, called "route handlers" there). Are you confusing features here?


Nope, just saying it's not something I need in the alternative. Doesn't need to be a full stack/backend framework - just focus on frontend and SSR.


Check out vite plugin ssr


> Pages and App toggles: You can switch between learning the Pages Router or App Router documentation using the button on the left side of the documentation. Further, you can filter search results based on your router choice.

Thank you so much for this! I recently gave up on trying to learn Next.js because the tutorial and the vast majority of the documentation only covered the "old" Pages Router way of doing things.


At my current gig we support two Next apps (both on the pages router) and are currently in the very early stages of building a new Next app using the app router. While we are very excited about the technology, adoption has been slowed by a few things.

1. Server components have poor support for certain (non tailwind) css solutions. We had hoped to use vanilla-extract as its syntacticly similar to other css-in-js solutions, but ran into issues with HMR completely falling apart locally if the page contained a NextImage. We ended up falling back to good ol’ fashion sass modules.

2. As some other commenters mentioned googling for support somewhat consistently lands you on the opposite routers docs and while it’s somewhat obvious to tell where you are its still missable if you are moving quick.

All that to say I’m personally, _sorta_ burnt on Next and have found a ton of joy using svelte + sveltekit for my personal/hobby projects.


Vercel as a hosting provider is almost purposely slow (at least on the free tier) for app router based sites. RSC files in particular take 500ms to 2000ms to start serving those static files.


The page load performance of a site on Vercel's free and paid tier should be the same. Both would be using Vercel's Edge Network and possible a Vercel Function if dynamically rendered. As mentioned in the post, we're working to improve loading performance in general with the Next.js App Router.


But the stuff is static. Just that RSC files are oddly slow which can prevent a page transition on a fast click.

And there isn’t a way to signify loading as those events on the router are gone.


lots of free tiers have slow start up times when an app has been idle

(eg: heroku and render)

Not 100% sure if this is what is causing that on Vercel, but seems fair to me for free tiers?


People definitely get what they pay for. Heroku was and still is notoriously slow, charging a massive premium for convenience. I'm obviously biased because I built a CD service for AWS, but I strongly believe that when a hosting service doesn't advertise what hardware resources you are actually getting, it's a trap.


It's backed by lambda that has cold start. Don't think that part has to do with free tiers.


App router itself is slow (slower than page router).


I find it absolutely annoying that cookie().set() is only available in Route Handler and this new beta server actions, but not the server page itself.]


Reading all this I'm so glad I took the bigger hurdle of rolling SSR myself on React without any frameworks.


Next and React have gotten way too complicated. I don't want to read twelve pages of documentation to understand how to understand the rest of the documentation.

I've been coding in React for 6 years and in Next for 3 years. My next project will be in Vue.


Your nuxt project will be Vue?


So, what's up with this. How it go from:

Javascript isn't sufficient... to React/Vue aren't sufficient... to Next/Nuxt are <insufficient? too complicated?>

Why didn't the bandwagon just end at the first layer of frameworks?


good correction


Why?


In general, any model that uses fine grained reactivity (Vue, Preact, Solid, Svelte) will be more "forgiving" then one that uses coarse grained reactivity (React) because it triggers smaller component tree updates.

This tends to reduce certain classes of bugs like side effects from unexpected re-renders and performance issues like over rendering.

The thing with React and Next is that it's great if your team is relatively homogeneous in terms of skill and experience or you have strong systems in place to enforce practices. However, the render cycle of React and the provider pattern is prone to bugginess otherwise. A firsthand example is Algolia's React components. Look at the GH issues. We ran into tons of issues related to unexpected redraws.


If re-renders are causing bugs, you are 100% holding the tool wrong

Like having data corruption issues from GET requests.

---

I prefer explicit, but if implicit fine grained reactivity is the sole point of concern, you might be interested in React+MobX.


Every React team I've worked with has held the tool wrong because on every project I've been on in 3 VC backed startups, I've had to track down unintended side effects.

MobX and Valtio create an illusion of fine-grained reactivity but do not change the underlying render cycle of React itself.


> Next and React have gotten way too complicated.

Because I'm fed up with all the unnecessary complexity, and I want to try Vue because it looks a lot less complex, and I've already had a positive experience in the ecosystem with Vite and Vitest.


I mean.... This just sounds like novelty.

You could keep using the react you've always liked?


Yeah, it's a good point, and I'll continue to do that on my stable projects. But for a new project I'd like to try Vue, because I don't like the direction React is moving. In five years the "React I like" might not be available or widely practiced.

You're right that Vue will be a novelty - that's what I'm saying: React has jumped the shark to the point that it's now worth trying something for its novelty, because it just might be better.


Anyone used the server streaming stuff fully yet? How are you finding it? Good? Or too many quirks and bugs?

Seems too a bit too beta atm.


NextJS is just a mess after all.

Nested folders routing is a mess. Overall the nextjs routing is a mess. It's vendor lockin. How can i use next router outside of nextjs ?

There's no progressive enhancement builtin. Your static html will always need to deliver that next-runtime. Why ? There must be something wrong at the foundation level.

There's no official guidance on how to do the Authentication. In NodeJS, we do have PassportJS!

I love RSC, React Streaming, React Suspense, but the way NextJS use it seems like vendor lockin (Vercel).

Want to use Babel, modify webpack with SWC compiler ? It's just confusing.

No more NextJS until they fixed the foundation.


I really want to like Next.js but as a recent adopter (within the last year) I’m not sure I’m going to stick with it.

I find the “new” way to write Next apps incredibly confusing. Everything is now a mix of server and client and there’s so much rendering complexity. Im sure for big ambitious companies this focus on performance is great, but I find that it greatly compromises developer experience.

I’ve also found the piecemeal transition to the new app router pretty challenging as I’ve had to feel around to find the issues (of which there have been a few)

That said, Vercel makes deployment so easy so I’ll probably stick around a while longer to see if things get ironed out.


I fear next.js has been infected, like many other incredibly successful projects, by the ever expanding feature-set to match the ever expanding popularity.

We have seen it all before and will continue to see it again.

> Any successful project will start by doing one thing, well, but end up doing many things, poorly.

https://bower.sh/bowers-law


They went on a hiring spree the last two years, trying to position themselves as the React framework, or rather, the only way to use React. It's evident in React's new docs, that explicitly recommend frameworks.


Data point of one; I am new to next.js and tried both new and old ways. Decided on new way since it's slightly less worse than old way and it's the new way forward. After a few weeks, I've decided to dump it and just go with Vite. I can sprinkle SSR on top of it w/ plugin if needed. Much faster, much simpler DX, much smaller build output. I regret choosing Next.js and regret the decision to use it believing it's at least a good/decent choice based on popularity and default choice for most people.


Dev mode is also a lot slower in app router (well so is production). HMR feels like a crawl even on a fast machine.


Sorry about this. Do you have a GitHub issue with a reproduction we can look into? This is our top priority. In the meantime, I'd recommend continuing to use the Pages Router.


What's a full-stack TypeScript-based alternative that's good enough for most of us? I constantly bump into the complexity of NextJS myself, but so far I've powered through the pain.


I searched far and wide a few months ago and found these two are the only real contenders:

RedwoodJS

Remix

If I had to compare them, I would label Redwood as more of an "emberjs" type feel, very corpo, angular-js, "enterprise". Remix is more loose and new, fresh ideas that other frameworks have since attempted to copy.

Pick your poison.


Have you considered Deno? First class TypeScript support, secure sandboxing, and JIT rendering for React/Preact style projects with Fresh (https://fresh.deno.dev).

Also, they recently introduced a Node compatibility feature that supports _most_ modules. You can import directly from NPM using the npm: specifier, or import (almost) all of the builtin Node APIs using the standard node: specifier. Since recent versions (1.30+) of Deno are bundled with whats essentially a Node clone, and since its all packaged as a ~32MB executable... I've found myself just using Deno for everything lately. So far its been able to handle all of the projects I used to run with Node.

Check out their docs: https://deno.land/manual


Vite with trpc? I personally don't use the backend functionality of NextJS at all, I have my own backend (in Rust but I'd do the same in Node as well) that communicates via GraphQL to the frontend in NextJS, it's pretty nice.


What are you doing with trpc if your backend is in Rust? trpc is typescript to typescript


I never said I was using trpc, I was simply answering the parent's question about NextJS alternatives. But even with Rust, you can use a similar project called rspc that creates TS types from Rust.


(Author) It took me a bit to get used to the new patterns of building with the App Router. It seems harder for folks who have lots of experience building with the previous mental model, versus starting new from scratch. Some unlearning needed.

Apologies that you've ran into a few issues trying things out. We're working hard to patch up some of these. If you have any specifics, please let me know and we can look into them.


You might want to consider Qwik which uses React syntax to create components and can be very easy to develop performant web applications


> Im sure for big ambitious companies this focus on performance is great

On the contrary, the performance with the new method is even worse.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: