I feel a poor tool choice for your use case should not give you the right to blast the tool and it's design decisions. Most of those complaints are resulting from not understanding how NextJS works and the design decisions that it's creators have made. For example, the middlewares. they're to be treated as a hook. If NextJS had a mechanism for having handlers like Express does, you'd have complained about handler execution order or something.
If you picked NextJS without knowing how it structures its middleware, the vendor lock-in to Vercel, its SSR strategy, its hydration schemes etc. that's on you. I, and many others, have had a lot of success with NextJS increasing delivery speed and ultimately, customer value.
Two years ago I moved off of the React ecosystem to Elixir/Phoenix/LiveView, and it's been great. But that's had its own challenges stemming from the design decisions its creators have made. You're always going to be running into things that you don't like, and I feel NextJS has just become an easy target for people who are looking to vent.
NextJS has been pushed aggressively by many people and often recommended as a kind of default for React applications. Which I consider a bad idea, in a large part because NextJS contains a lot of complexity that most applications don't need.
the React documentation is infamously responsible of recommending Next as a "default". After a lot of backlash it got somewhat toned down, but it's still the first thing they suggest[1] for creating a new app
[1] https://react.dev/learn/creating-a-react-app
I'm sorry, but please do read the post.
The middleware section is a setup. The real trouble starts when ejecting from Next and using a custom server still doesn't allow you to do anything because Next is a black box.
I would have been happy with installing fastify and just using it's middleware, but even that doesn't work.
What challenges did you pick up with Elixir?
Elixir/Phoenix is awesome, no complaints overall. A few small things:
- Passing data from LiveComponent's/JS is a bit of a pain (need to use update())
- phx-hook doesn't always pay well with re-rendering state changes
- Directly calling JS functions (e.g, getting Apple Pay to work) isn't clean
- Can't use attr when using LiveComponents (need to wrap them in a functional component)
- Unique ID requirement for LiveComponent is a pain (so is wrapping them in a div)
- No great APIs for updating session data when using sockets
- Can't pass params to LiveView in live_render, have to use session