useActionState
is a hook that allows you to update state based on the result of a form action.
It's currently only available in Reactβs Canary and experimental channels. In addition, you need to use a framework that supports React Server Components to get the full benefit of useActionState.
It simplifies managing form state updates based on server-side actions. It's particularly useful with React Server Components (RSC) for faster response times.
π Basic example
The most simple example to understand the concept would be that of a form that increments a counter.
import { useActionState } from "react";
async function increment(previousState, formData) {
return previousState + 1;
}
function StatefulForm({}) {
const [state, actionToTake] = useActionState(increment, 0);
return (
<form>
{state}
<button formAction={actionToTake}>Increment</button>
</form>
)
}
As you can see the form takes two arguments
- An action function that handles form submission and interacts with the server.
- An initialState object representing the initial form state.
- The action function itself will receive two arguments - previousState and the formData. In the first call the previousState will be the initialState that would have been initialized when useActionState was called.
And it returns an array containing
- The current form state object
- a
actionToTake
(you can rename it to whatever makes most sense - see example below) function that you can use as a buttonformAction
handler (example above) oraction
handler in form component itself (example below).
π‘ When
<form>
is rendered by a Server Component, and a Server Action is passed to the<form>
βs action prop, the form is progressively enhanced. This means that forms can be submitted before the JavaScript bundle is loaded π₯
π Example with server actions
Another interesting property the hook returns is the isPending
property which can help handle loading states.
// actions.js
'use server'
export default async function incrementLike(prevState, data) {
// Simulate delay
return new Promise((resolve, reject) =>
setTimeout(() => resolve(prevState + 1), 3000)
)
}
//like.js
'use client'
import incrementLike from './actions'
import { useActionState } from 'react'
function LikeButton() {
const [likes, likeCountAction, isPending] = useActionState(incrementLike, 0)
return (
<>
<p>Total Likes: {likes}</p>
<form action={likeCountAction}>
<button
type='submit'
disabled={isPending}
className="border box-shadow bg-[#fff] p-4 disabled:opacity-50 disabled:cursor-not-allowed"
>
Like
</button>
</form>
</>
)
}
π Key Takeaways
-
useActionState
simplifies managing form state based on server-side actions. - It's particularly useful with React Server Components (RSC) for faster response times.
- It offers functionalities like isPending to handle loading states during server interactions.
π Things to Keep in Mind
-
useActionState
is currently experimental and might change in future releases. - You need a framework that supports React Server Components to utilize the full potential of this hook.
Happy coding!
Top comments (1)
_Great _