patternjavascriptvueTip
Vue 3 keep-alive caches component state across route changes
Viewed 0 times
Vue 3.0+
keep-alivecomponent cachingonActivatedonDeactivatedscroll positionvue router cache
Problem
Switching between routes destroys and recreates components, losing scroll position, form state, and fetched data. Without keep-alive, every visit reruns the setup logic.
Solution
Wrap router views with <KeepAlive> and handle activation hooks:
<!-- App.vue -->
<template>
<RouterView v-slot="{ Component }">
<KeepAlive :include="cachedViews" :max="10">
<component :is="Component" :key="$route.path" />
</KeepAlive>
</RouterView>
</template>
<script setup>
import { ref } from 'vue';
// Only cache these named components
const cachedViews = ref(['ListView', 'SearchView']);
</script>
<!-- In a cached component -->
<script setup>
import { onActivated, onDeactivated } from 'vue';
onActivated(() => {
// Called each time the component becomes visible again
refreshData(); // re-fetch stale data
});
onDeactivated(() => {
// Called when leaving but not destroyed
pauseVideoPlayback();
});
</script>
<!-- App.vue -->
<template>
<RouterView v-slot="{ Component }">
<KeepAlive :include="cachedViews" :max="10">
<component :is="Component" :key="$route.path" />
</KeepAlive>
</RouterView>
</template>
<script setup>
import { ref } from 'vue';
// Only cache these named components
const cachedViews = ref(['ListView', 'SearchView']);
</script>
<!-- In a cached component -->
<script setup>
import { onActivated, onDeactivated } from 'vue';
onActivated(() => {
// Called each time the component becomes visible again
refreshData(); // re-fetch stale data
});
onDeactivated(() => {
// Called when leaving but not destroyed
pauseVideoPlayback();
});
</script>
Why
KeepAlive wraps components in an internal cache instead of destroying them. onActivated/onDeactivated fire instead of onMounted/onUnmounted for cached components. This preserves scroll position, form input, and avoids expensive re-fetches.
Gotchas
- The component must have a name option (or <script setup> filename) for :include/:exclude to match
- :max evicts the least recently used component when the cache exceeds the limit
- onMounted/onUnmounted still fire the first mount and final destroy
- Memory usage grows with cached components — always set :max for route-level caching
Code Snippets
KeepAlive with route transition
<RouterView v-slot="{ Component }">
<Transition name="fade">
<KeepAlive :max="5">
<component :is="Component" />
</KeepAlive>
</Transition>
</RouterView>Context
When preserving component state across route navigation in Vue 3
Revisions (0)
No revisions yet.