What does toRefs() do?
1. What toRef() does
The toRef() function creates a reactive reference (ref) to a specific property of a reactive object.
It does not copy the value, it links .value directly to the source property.
That is, changes in the original object are reflected in the ref, and vice versa.
Example:
import { reactive, toRef } from 'vue'
const state = reactive({ count: 0 })
const countRef = toRef(state, 'count')
console.log(countRef.value) // 0
countRef.value++ // increased through the ref
console.log(state.count) // → 1 (the original object changed too)
state.count = 5
console.log(countRef.value) // → 5 (the ref changed too)Important:
toRef() does not create new reactivity, it is just a "pointer" to an already reactive property.
2. What toRefs() does
The toRefs() function does the same thing, but for all properties of an object at once.
It returns an object of refs, where each field is linked to the corresponding property of the original.
Example:
import { reactive, toRefs } from 'vue'
const state = reactive({
count: 0,
name: 'Tim'
})
const { count, name } = toRefs(state)
count.value++ // changed through the ref
console.log(state.count) // → 1
state.name = 'Alex'
console.log(name.value) // → 'Alex'Now count and name are ref wrappers linked to state.
3. Why they are needed
The most common case is destructuring reactive objects.
If you do this:
const state = reactive({ count: 0, name: 'Tim' })
const { count, name } = stateYou lose reactivity,
because count and name become plain copies of the values (a number and a string).
The solution is to use toRefs():
const { count, name } = toRefs(state)Now count and name are reactive ref references that stay synchronized with state.
4. Difference between toRef() and toRefs()
| Criterion | toRef() | toRefs() |
|---|---|---|
| What it does | Creates a ref for one property of a reactive object | Creates a ref for all properties of an object |
| Returns | A single ref | An object where each field is a ref |
| Used when | You need a reference to one field | You need to destructure the whole object |
| Syntax | toRef(obj, 'key') | toRefs(obj) |
| Loses reactivity on destructuring | No | No (for all properties) |
5. How it works under the hood
Simplified (from Vue's source):
function toRef(object, key) {
return {
get value() {
return object[key]
},
set value(newVal) {
object[key] = newVal
}
}
}And toRefs() simply calls toRef() for each key:
function toRefs(obj) {
const result = {}
for (const key in obj) {
result[key] = toRef(obj, key)
}
return result
}So these are not new reactive() or ref() instances, they are "thin bridges" between the object's fields and their values.
6. A real-world usage example (in setup())
import { reactive, toRefs } from 'vue'
export default {
setup() {
const state = reactive({
count: 0,
name: 'Tim'
})
// so it can be returned destructured into the template:
return {
...toRefs(state)
}
}
}Now in the template you can write:
<template>
<p>{{ count }}</p> <!-- automatically count.value -->
<button @click="count++">+</button>
</template>Without toRefs() this would not work, count would lose reactivity after destructuring.
7. A nuance: toRef() can be used on its own
For example, to pass a single reactive property to a child component:
const user = reactive({ name: 'Tim', age: 25 })
const nameRef = toRef(user, 'name')
// we pass only nameRef, but it is still linked to user.nameIf you had passed plain user.name, reactivity would be lost.
8. What happens when you call toRef() for a non-existent property
Vue creates an empty ref(undefined),
and writing to .value adds a new property to the source object:
const state = reactive({})
const age = toRef(state, 'age')
console.log(age.value) // undefined
age.value = 30
console.log(state.age) // 309. Summary
| Function | What it does | When to use it |
|---|---|---|
toRef(obj, key) | Creates a ref linked to obj[key] | When you need to work reactively with one property |
toRefs(obj) | Converts all properties of an object into refs | When you need to destructure a reactive object and keep reactivity |
In short:
toRef()makes one reactive "reference" to a property.toRefs()makes a set of such references.Both exist so you don't lose reactivity when destructuring or passing data between components.
Short Answer
Interview readyA concise answer to help you respond confidently on this topic during an interview.