ref vs reactive: When to Use Each
ref.value access, reactive unwrapping in templates, toRefs(), toRef() for destructuring.
ref vs reactive: When to Use Each is a free Vue Academy lesson on CoddyKit. This is lesson 3 of 4. Any 3 lessons of this learning path are free to read in full — after that, CoddyKit PRO unlocks every lesson, plus hands-on practice with a built-in code editor and a 24/7 AI tutor. It is part of the Vue Academy learning path, and your progress syncs across the web and the CoddyKit app. The Vue Academy course includes 4 lessons in total.
Two Reactivity Tools
Vue offers two main ways to create reactive state: ref() and reactive(). They overlap, but each fits certain situations better. Knowing when to reach for which keeps your code clean.
ref Works with Any Value
ref() can wrap anything: a number, string, boolean, array, or object. The value lives on .value in JavaScript.
import { ref } from 'vue'
const count = ref(0)
const name = ref('Alice')
const isOpen = ref(false)
count.value++
name.value = 'Bob'ref Auto-Unwraps in Templates
While you must write .value in JavaScript, the template auto-unwraps a top-level ref. So {{ count }} just works.
<!-- template -->
<p>{{ count }} - {{ name }}</p>reactive Is for Objects
reactive() only accepts objects (including arrays and Maps). It returns a deeply reactive proxy and you access properties directly — no .value.
import { reactive } from 'vue'
const state = reactive({
name: 'Alice',
age: 30,
hobbies: ['reading']
})
state.age = 31
state.hobbies.push('coding')reactive Is Deeply Reactive
Nested objects and arrays inside a reactive object are also reactive. Mutating a nested property triggers updates without extra work.
const state = reactive({ profile: { city: 'Paris' } })
state.profile.city = 'Berlin' // reactive!The reactive Limitation: Destructuring Breaks It
If you destructure a reactive object, the extracted variables become plain values and lose reactivity. This is the number one gotcha.
const state = reactive({ name: 'Alice' })
let { name } = state
name = 'Bob'
// state.name is still 'Alice' - reactivity lost!The Fix: toRefs for Safe Destructuring
toRefs() converts each property of a reactive object into a ref. Now you can destructure and keep reactivity, because each piece is a ref linked back to the source.
import { reactive, toRefs } from 'vue'
const state = reactive({ name: 'Alice', age: 30 })
const { name, age } = toRefs(state)
name.value = 'Bob' // state.name is now 'Bob'toRef for a Single Property
If you only need one property as a ref, use toRef(state, 'key'). It stays in sync with the source object both ways.
import { reactive, toRef } from 'vue'
const state = reactive({ age: 30 })
const age = toRef(state, 'age')
age.value = 31 // state.age is now 31A Practical Rule of Thumb
- Use
ref()for primitives (numbers, strings, booleans) and standalone values. - Use
reactive()for a group of related properties that form one object. - When returning a reactive object from a composable, wrap it in
toRefs().
ref Can Also Hold Objects
You are not forced to choose reactive for objects. A ref holding an object is also deeply reactive — you just access it through .value. Many teams use ref everywhere for consistency.
const user = ref({ name: 'Alice' })
user.value.name = 'Bob' // reactive
user.value = { name: 'Carol' } // replace whole objectSummary Table
- ref: any value, needs
.valuein JS, auto-unwraps in template, can be reassigned wholesale. - reactive: objects only, no
.value, deeply reactive, but breaks on destructure and cannot be reassigned. - toRefs: bridge that makes reactive properties destructurable.
Quick Check
Pick the right tool.
Recap
Key takeaways:
ref()wraps any value and needs.valuein JavaScript.reactive()is for objects and is deeply reactive, but destructuring breaks it.toRefs()lets you safely destructure a reactive object.- Use ref for primitives, reactive for grouped object state.
Learn HTML with an AI tutor — free
Write and run real code in your browser, get instant help from a 24/7 AI tutor, and pick up where you left off on the web or in the app.
- Courses
- 42
- Lessons
- 156
Frequently Asked Questions
Is the “ref vs reactive: When to Use Each” lesson free?
Yes — any 3 lessons of the Vue Academy learning path, including “ref vs reactive: When to Use Each”, are free to read in full here on the web. After that, CoddyKit PRO unlocks every lesson, plus interactive practice with a built-in code editor and a 24/7 AI tutor. The Vue Academy course includes 4 lessons in total.
What will I learn in “ref vs reactive: When to Use Each”?
ref.value access, reactive unwrapping in templates, toRefs(), toRef() for destructuring. You practise Vue Academy with hands-on code you run directly in the browser, and a 24/7 AI tutor answers your questions as you work through the lesson.
Do I need any experience to start Vue Academy?
No prior experience is required. Vue Academy on CoddyKit is structured for beginners through advanced learners, so you can start here or from the beginning and move at your own pace. This is lesson 3 of 4.
How long does the “ref vs reactive: When to Use Each” lesson take?
Most CoddyKit lessons take about 5–10 minutes. Each one is bite-sized and interactive, so you make steady progress and pick up exactly where you left off across the web and the app.
Can I write and run code in this Vue Academy lesson?
Yes. Every Vue Academy lesson includes a built-in code editor, so you write and run real code right in your browser and get instant AI feedback — no local setup required.
All lessons in this course
- Why Composition API?
- setup() Function and Reactive Variables
- ref vs reactive: When to Use Each
- Computed and Watch in Composition API