
*By Sean Erick C. Ramones, Vue SME | JavaScript/TypeScript SME*
Sean Erick C. Ramones
useAsyncData() and useFetch() now share the same reactive state (ref) across components when using the same key.
<!-- ComponentA.vue -->
<script setup>
const { data: users, pending } = useAsyncData('users', fetchUsers)
</script>
<!-- ComponentB.vue -->
<script setup>
const { data: users, status } = useAsyncData('users', fetchUsers)
// Updates in A reflect here in real-time
</script>
✅ Benefit:
Avoids duplicate API calls and ensures a consistent UI state across the app.
Keys passed to useAsyncData() can now be ref, computed, or dynamic getters, triggering automatic refetching when dependencies change.
<script setup>
const userId = ref('123')
const { data: user } = useAsyncData(
computed(() => `user-${userId.value}`),
() => fetchUser(userId.value)
)
userId.value = '456' // Auto-fetches new data and cleans old entry
</script>
✅ Benefit:
Simplifies dynamic data workflows and improves memory cleanup.
When using the same key across components with dynamic inputs, Nuxt ensures only one fetch call is made and shared state is updated everywhere.
<script setup>
const page = ref(1)
const { data: users, pending } = useAsyncData(
'users',
() => $fetch(`/api/users?page=${page.value}`),
{ watch: [() => page.value] }
)
</script>
✅ Benefit:
Efficient updates across all components without redundant fetches.
Nuxt introduces the experimental.granularCachedData flag for finer control over data caching and purging behavior.
// nuxt.config.ts
export default defineNuxtConfig({
experimental: {
granularCachedData: true
}
})
You can also disable purgeCachedData to keep older caching behavior if needed.
New compile-time warnings for:
definePageMeta calls✅ Benefit:
Improves visibility and reduces runtime errors during development.
| Feature | Benefit |
|---|---|
| Shared Data Refs | Unified state across components |
| Reactive Keys | Smarter dynamic fetches |
| Deduped Requests | Prevents redundant API calls |
| Granular Cache Control | More flexible fetch behavior |
| DX Warnings | Surfaces issues early during build time |
export default defineNuxtConfig({
experimental: {
granularCachedData: true
}
})
useAsyncData() and useFetch():ref/computed keys if needed.watch arrays to support dynamic inputs.defineNuxtConfig({
experimental: {
purgeCachedData: false
}
})
npx nuxi@latest upgrade --dedupe
| Trade-off | Consideration |
|---|---|
| Additional config complexity | Some new caching flags to learn and test |
| Potential early bugs | Recent rewrite may have edge cases under refinement |
| Slight migration overhead | Dynamic keys may require key refactoring |
Nuxt 3.17 introduces a smarter, more reactive async data layer with shared state, automatic deduplication, and better dynamic key support. It's a strong step forward for data handling in Nuxt apps and is recommended for teams working on scalable, performant Vue applications.