Javascript is required
Michael Hoffmann LogoMichael Hoffmann

Vue Tip: Optimize Performance Using shallowRef

Michael Hoffmann - Senior Frontend Developer (Freelancer)
Michael Hoffmann
Apr 7, 2023
1 min read
|
59 views
Script
Performance
Vue Tip: Optimize Performance Using shallowRef Image

shallowRef can be used to optimize the reactivity of your Vue application. As you might have guessed, shallowRef is a shallow version of ref().

Let's start by defining a counter state using shallowRef:

Component.vue
<script setup lang="ts">
import { shallowRef } from 'vue'

const state = shallowRef({
  count: 0,
})
</script>

<template>
  <span>Count: {{ state.count }}</span>
</template>

Now let's try to modify the count value:

Component.vue
<script setup lang="ts">
import { shallowRef, watch } from 'vue'

const state = shallowRef({
  count: 0,
})

const increment = () => {
  state.value.count = 2 // ⚠️ doesn't trigger change (watcher & UI update)
}

watch(state, (newState) => {
  console.log('new state', newState)
})
</script>

<template>
  <span>Count: {{ state.count }}</span>
  <button @click="increment">Increment count</button>
</template>
Be careful

If you click the "Increment count" button the counter in the UI is not updated and the watcher is not fired.

Unlike ref(), the inner value of a shallow ref is stored and exposed as-is, and will not be made deeply reactive. Only the .value access is reactive.

The reactivity is correctly triggered if we pass a complete new value to the .value property:

Component.vue
<script setup lang="ts">
import { shallowRef, watch } from 'vue'

const state = shallowRef({
  count: 0,
})

const setNewValue = () => {
  state.value = { count: 2 } // triggers change
}

watch(state, (newState) => {
  console.log('new state', newState)
})
</script>

<template>
  <span>Count: {{ state.count }}</span>
  <button @click="setNewValue">Set new .value</button>
</template>

shallowRef() is typically used for performance optimizations of large data structures, or integration with external state management systems.

Info

Try it yourself in the following StackBlitz project:


If you liked this Vue tip, follow me on Twitter to get notified about new tips, blog posts, and more. Alternatively (or additionally), you can subscribe to my weekly Vue newsletter:

New Vue & Nuxt tips delivered to your inbox:
I will never share any of your personal data.