Actions and forms
Create a Server Action
Connect a form to an asynchronous server function without writing a separate client-side request handler.
React lets a form call a Server Function through its action prop. In a mutation context that function is commonly called a Server Action.
Mark the async function with "use server", inline in a Server Component or at the top of a dedicated actions file. The browser sends a POST request behind the scenes. Keep authorization and validation inside the action because a user can invoke the server endpoint without using your rendered form.
With a Server Component form, the browser can submit before client JavaScript loads, so the basic mutation can work as plain HTML. A form rendered inside a Client Component may queue submission until hydration. Do not make correctness depend on that queue or on a disabled button alone.
Treat every action as a public mutation endpoint. Hidden inputs and IDs bound into an action are user-controlled intent, not authorization. Read the current user on the server, check access to the specific record, validate the full payload, and return only safe serializable state.
async function createNote(formData: FormData) {
'use server'
const title = formData.get('title')
console.log('received title:', title)
// validate, authorize, then write
}
export default function Page() {
return (
<form action={createNote}>
<input name="title" defaultValue="Morning walk" />
<button>Save</button>
</form>
)
}
Submit the form and check the server terminal. You should see received title: Morning walk. Disable JavaScript in the browser and submit again. The POST should still reach the server.
Then forge a request with a note ID your UI never showed. The server should reject it even though the visible form looked innocent.
Watch the Network tab on submit: you should see a POST to the current route with multipart/form-data, not a hand-written fetch from client code you maintain separately.
Server Actions also work from buttons via the formAction prop when one page needs multiple mutations. The same authorization rules apply to every entry point.
Lesson completed