Query Ownership and Caching
Understand where query results live without creating a second state authority.
“Cache” can refer to several different owners in one Nuxt page. Distinguishing them prevents duplicate state.
Where state lives
| State | Owner | Lifetime |
|---|---|---|
| Convex query result and wire deduplication | Current Convex client | Client lifetime and identity generation |
| SSR result | Nuxt payload/async data | Request and hydrated payload |
data, error, and lifecycle refs | Composable instance | Vue effect scope |
| Optimistic local view | Convex client local store | Until server confirmation or rollback |
| UI-only state | Component or app store | Application-defined |
There is no separate Better Convex Nuxt entity cache or query registry.
Identical queries
Two mounted components may request the same Convex query and arguments. Convex owns wire-level deduplication. Each composable still has its own Vue-visible refs, which keeps loading presentation and derived views local to their consumers.
For reusable application intent, write an ordinary composable that calls the query directly:
import { api } from '#convex/api'
export function useCurrentTeam() {
return useConvexQuery(api.teams.current, {}, { auth: 'required' })
}This is code reuse, not a second cache owner.
Reactive argument identity
A query is identified by its function reference, normalized arguments, auth boundary, and current identity generation. Changing arguments requests a new result.
keepPreviousData: true may retain the previous result while new arguments load for the same identity. It never carries data across an identity boundary.
Convex data versus Pinia
Keep server-backed entities in Convex queries. Use Pinia or local refs for UI state such as:
- open panels and dialogs;
- unsaved local drafts;
- wizard progress;
- client preferences that are not server data.
Copying query entities into Pinia creates synchronization work: refresh, optimistic rollback, sign-out clearing, and live update reconciliation all gain a second implementation.
No cross-request cache promise
Each server request has its own Nuxt app and identity context. If a deployment adds HTTP or page caching, its privacy and invalidation rules belong to that deployment layer. Read performance before caching authenticated pages.