Next.js 15 Server Actions in Production: What We Learned
By DEV3 Engineering
Server Actions let a form post straight to a server function without a hand-written API route. On the projects we have shipped with them this year, they cut the code needed for CRUD screens by roughly a third. The hard parts did not go away, though. They moved.
Validate at the boundary, every time
A Server Action is a public HTTP endpoint, whatever the code makes it look like. We parse every FormData payload with a shared zod schema before any database call. We keep those schemas in a separate module, so client components can reuse them for instant feedback.
Our production checklist
- Validate input with a schema, and return field-level errors in the action's state.
- Check authentication and authorisation inside the action. Never rely on the page alone.
- Rate-limit actions that anyone can call, such as contact and signup forms.
- Call revalidatePath or revalidateTag only for the data that actually changed.
- Log failures with context, but never echo raw database errors back to the user.
Combined with useActionState, these rules give you progressive-enhancement forms with pending states and inline errors, and you don't need a client-side form library.