Composition API'S was introduced in vue from 2.7 version to replace options API'S.
On of These API's is Reactivity api ('ref'
and 'reactive'
) to declare reactive state, instead of data function in option API.
This new API is the backbone of composables.
What are composables?
Composables are functions based on reactivity api following a specific structure making it possible for developers to separate stateful or stateless logic from components.
In addition, logic itself could be split in different composables and nested together to achieve a specific task on account of the fact that composables are 'malleable' through arguments.
Composables examples:
Composable have three major parts:
Internal state: Any state related to the function.
States that will be exposed must be reactive using 'ref'
or 'reactive'
.
Nevertheless, it is recommended to use 'ref'
since it retains reactivity and enables destructuring in components straightforward compared to 'reactive'
.
Manage state: A logic to apply when an action happens
Return state: Expose managed state
Composable returns an object with single value or multiple values, a value could be a method.
1. Basic composable
In the example below useIsUserActive
is a composable to check if a user click somewhere in the page.
Then imported and executed in vue component.
You may notice that composable name starts with use
as it is the naming convention from vuejs team.
2.Composable with returned methods:
Let's see more sophisticated example: useTimer
This composable will act as a timer that we can control through different methods: start
, pause
and stop
.
3.Composable with arguments:
Composable could be parametrized as the example below.
This composable is responsible for replacing spaces in strings with specific separator.
data
andseparator
are the parameters.watchEffect
will be run whenever one of its dependencies change. WithoutwatchEffect
our function will run only the first time even thoughdata
orseparator
have been changed.
Its dependencies must be reactive to be capable of doing this job, for that reasondata
andseparator
must be a ref.toValue
is a function that returns either:
1.Normalized value
of the source if that source is a ref
.
2.Execute the function of the source and returns its value if
that source is a getter function.
3.Returns value
of the source if that source is a normalized
value.
Composables advantages:
Let's use useTimer
composable logic straight inside the component.
<script setup lang="ts">
import { ref } from "vue"
const timer = ref(0)
let myInterval: number
// start method
const start = () => {
myInterval = setInterval(() => {
timer.value = timer.value + 1
}, 1000)
}
// pause method
const pause = () => {
clearInterval(myInterval)
}
// stop method
const stop = () => {
timer.value = 0
clearInterval(myInterval)
}
</script>
<template>
<main>
{{ timer }}
<button @click="start()">start</button>
<button @click="pause()">pause</button>
<button @click="stop()">stop</button>
</main>
</template>
You will notice that the component does not care of timer state, then it does not make any sense for the component to have access to timer logic.
You will not be capable of reuse this logic unless you copy paste.
Imagine this component get bigger, it will be more difficult to debug.
As you may notice this technique will offer lighter components regarding components complexity and length. Besides easier debugging.
Conclusion:
Composables are the new way of reuse and encapsulate logic in vuejs application. They gain this power from composition api the thing that take vuejs application to another level.
Implementing composables, from personal use in several projects, won't cost neither ambiguity nor new layer of complexity compared to their advantages.
You find the examples above in my github: Github