typescriptadvanced
React Optimistic Update Pattern
Implement optimistic UI updates that show changes immediately and rollback on server failure.
typescriptPress ⌘/Ctrl + Shift + C to copy
'use client';
import { useState, useCallback, useTransition } from 'react';
interface Todo {
id: string;
text: string;
completed: boolean;
}
// Simulated API
async function apiToggleTodo(id: string): Promise<Todo> {
const res = await fetch(`/api/todos/${id}/toggle`, { method: 'PATCH' });
if (!res.ok) throw new Error('Failed to update');
return res.json();
}
async function apiDeleteTodo(id: string): Promise<void> {
const res = await fetch(`/api/todos/${id}`, { method: 'DELETE' });
if (!res.ok) throw new Error('Failed to delete');
}
function useTodos(initial: Todo[]) {
const [todos, setTodos] = useState<Todo[]>(initial);
const [isPending, startTransition] = useTransition();
const toggleTodo = useCallback(async (id: string) => {
// Optimistic update
const previous = todos;
setTodos((prev) =>
prev.map((t) => (t.id === id ? { ...t, completed: !t.completed } : t))
);
try {
const updated = await apiToggleTodo(id);
setTodos((prev) => prev.map((t) => (t.id === id ? updated : t)));
} catch {
// Rollback on failure
setTodos(previous);
}
}, [todos]);
const deleteTodo = useCallback(async (id: string) => {
const previous = todos;
setTodos((prev) => prev.filter((t) => t.id !== id));
try {
await apiDeleteTodo(id);
} catch {
setTodos(previous);
}
}, [todos]);
return { todos, toggleTodo, deleteTodo, isPending };
}
// Component
function TodoList({ initial }: { initial: Todo[] }) {
const { todos, toggleTodo, deleteTodo } = useTodos(initial);
return (
<ul>
{todos.map((todo) => (
<li key={todo.id} className="flex items-center gap-2 p-2">
<input
type="checkbox"
checked={todo.completed}
onChange={() => toggleTodo(todo.id)}
/>
<span className={todo.completed ? 'line-through text-gray-500' : ''}>
{todo.text}
</span>
<button
onClick={() => deleteTodo(todo.id)}
className="ml-auto text-red-400"
>
Delete
</button>
</li>
))}
</ul>
);
}Use Cases
- Instant UI feedback for server operations
- Todo and task list toggle/delete patterns
- Like/bookmark with automatic rollback
Tags
Related Snippets
Similar patterns you can reuse in the same workflow.
typescriptadvanced
Optimistic Update Pattern
Apply UI changes immediately before server confirmation with automatic rollback on failure.
Best for: Like/upvote buttons
#optimistic-update#state
typescriptbeginner
usePrevious Hook
Track the previous value of any state or prop using a ref-based hook for comparison logic.
Best for: Detecting value changes
#hooks#state
typescriptintermediate
useUndoRedo State History Hook
Add undo/redo capability to any state with history tracking, max size limits, and keyboard shortcuts.
Best for: Text editor undo/redo
#react#hooks
typescriptbeginner
useToggle Hook
Simple boolean toggle hook with set, toggle, on, and off functions.
Best for: Modal open/close state
#hooks#state