#optimistic updates
5 messages · Page 1 of 1 (latest)
Hi @raven rover. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave:
Convex’s built‑in optimistic updates (withOptimisticUpdate) only apply to the Convex React client (convex/react hooks like useQuery, usePaginatedQuery). They don’t integrate directly with TanStack Query’s own optimistic update APIs. [TanStack adapter]
So you have two basic options:
1. Use Convex optimistic updates for Convex‑backed UI
If the part of your UI is already using Convex React hooks, use:
const myMutation = useMutation(api.my.mutation).withOptimisticUpdate(
(localStore, args) => {
// update Convex queries here
}
);
These updates:
- Run when the mutation starts
- Re‑run whenever relevant query snapshots change
- Roll back when the mutation finishes [React optimistic; ReactMutation]
However, there can be a small delay because the optimistic update only runs as often as your mutation is invoked or re‑run by subscription updates. If you want “every keystroke” style updates, Convex docs recommend maintaining extra local state in React alongside the optimistic update: [Single‑flight optimistic]
“If you want to update local state faster than the mutations are being executed, you’ll need to manage that state separately.”
Pattern:
const myMutation = useMutation(api.my.mutation);
const [localItems, setLocalItems] = useState<Item[]>([]);
const send = useCallback((data: ItemInput) => {
// Instant UI update
setLocalItems((prev) => [...prev, { ...data, localOnly: true }]);
// Fire mutation (optionally also withOptimisticUpdate on Convex queries)
void myMutation(data);
}, [myMutation]);
Then render convexData + localItems, similar to what’s recommended for paginated-chat optimistic sends when built‑in paginated helpers aren’t enough. [Paginated optimistic workaround]
2. When using TanStack Query (@convex-dev/react-query)
TanStack integration is for reading Convex queries (convexQuery(...) into useQuery). [TanStack adapter] It doesn’t expose a TanStack‑style mutation/optimistic API around Convex mutations.
So with TanStack Query you typically:
- Still call Convex mutations with
useMutationfromconvex/react(optionally.withOptimisticUpdatethat updates Convex queries), or - Use pure React state for ultra‑fast local UI and let Convex reactivity bring the true data in shortly after, as above.
Trying to use TanStack’s onMutate/setQueryData for Convex subscriptions isn’t documented in these sources, so I can’t give a supported pattern there.
Why you see “a tiny bit of lag”
From the docs and stack article:
- Optimistic updates only run when the mutation runs or when Convex pushes a new query snapshot.
- If your UI interaction frequency is higher (e.g. many rapid edits, typing, or multiple chat messages very quickly), some UI states never go through an optimistic update, so you feel latency. [Single‑flight optimistic]
The recommended way to remove that last bit of lag is:
- Use
withOptimisticUpdateto keep Convex queries feeling fast once they’re updated. - Layer pure local React state on top for the ultra‑immediate feel, accepting that some intermediate local states never hit the server. [Single‑flight optimistic]