
Many design decisions around server actions seem stupid
1. Forced sequential and disabled parallel execution. Why?
It is huge constraint. If I need something to be sequentially executed, I would just do await await await anyway.
Sometimes, on frontend, I need to call multiple longer tasks in parallel (like image generation) or fetch many things at once.
I understand that "data fetching" is intended to be done inside server components, but many times I need to fetch data dynamically during some client side interaction, inside client components.
In mentioned cases, server actions suck.
2. Version skew and inability to provide custom function id. Why?
On every redeploy server actions get new id, which creates errors for users who opened website before that (and loaded old ids).
This is huge pain in the a**.
Why are we not able to just provide our id, and change it when we feel it is needed?
3. All checks (like rate limit and auth) can be done ONLY after full body was parsed and loaded into RAM. Why?
I want to load body only if request passes rate limit and auth check. It does not make sense to do it before and waste hosting resources (RAM, CPU...).
Further more, loading whole body into RAM before mentioned checks opens big opportunity for denial of service attacks and similar.
4. Forcing POST requests and mutations as only intended use. Why?
Why can't we specify which type of request certain server action will be?
5. Relying on "use server" directive at top of the file instead of having special function for creating server actions. Why?
Maybe just personal preference, but I like more how it is done inside TanStack start. Much more DX friendly.
So, all mentioned problems with NextJS server actions are solved in TanStack start:
- server function creation and usage: link
- customizable ids persisted during deployments (not ideal, but still better): link
Why NextJS seems so stupid about all this?
Why NextJS does not have some good general purpose remote procedure call (RPC) system, like TanStack start?
Yeah, there is tRPC etc, but it has lots of boilerplate and it's not native framework thing.