The Vue JavaScript framework is "reactive," which means it can automatically refresh your data. Learn the ways you can take advantage of this in your apps.
Modern web applications need to render data dynamically in various HTML elements. Various frameworks like jQuery, React, Angular or Vue provide specific mechanisms to address this requirement and simplify the life of a programmer with high level functionality. In particular, the Vue framework provides a Reactive mechanism to display that data, and most importantly, a mechanism to take care of automatically refreshing the UI "when needed."
This raises the question: what is meant by “when needed”? Read on to get an explanation.
How the Vue Reactivity System Works
Vue provides three kinds of properties for rendering data inside HTML elements in a so-called Reactive manner. These are:
- Properties
- Computed properties
- Methods
It’s important to understand how Vue treats each one and particularly how it caches these, as it will have an impact on how often and when the functions will be called.
In this post, we'll review (via a sample) how to use data properties, computed properties and methods, as well as the differences between each one of them in terms of caching.
To follow along, just download this HTML file from Github. This sample is self-contained (It contains both the HTML and the Javascript code as well as references to all required dependencies).
Using a Data Property
The first mechanism to render data in your page is to use a data property.
In the first part of the HTML file we use two properties: startupDate and message
1.
<
div
v-bind:title
=
"startupDate"
>
2.
A property:
3.
<
span
id
=
"id1"
style
=
"font-weight: bold;"
>
4.
{{ message }}
5.
</
span
>
6.
….
7.
</
div
>
These are defined when initializing the Vue object with a data object literal like this:
data: {
message:
'Hello Vue! - This is Vue version: '
+ Vue.version,
startupDate:
new
Date().toLocaleString(),
…
},
At run-time, the div element will be adjusted to replace the two properties with their actual values, producing an output like this:
A property: Hello Vue! - This is Vue version: 2.5.16
At this point you could go to the browser console and enter something like: app.message = "Hi"
The output would then be changed to:
A property: Hi
This is the Reactive nature of Vue: automatically detecting that a property has changed and re-rendering the affected element. This is also called one-way data binding to indicate that the element is bound to the value of a property. It’s bound one way, that is, in the direction of the Vue data towards the span with id=”id1”. It is not bound in the other direction. For example, if you try to change the content of that span via Javascript, it won’t change the content of the data variable.
You can check this by typing this into your console:
1.
document.getElementById("id1").textContent = "abc"
2.
app.message // verify message has not changed
Interestingly, you can also bind an HTML element to a data property using JavaScript as long as you do it before the Vue object is created. This is what we do to span id=”id2” with this code:
document.getElementById(
"id2"
).textContent =
"{{ message }}"
;
Using Computed Properties
The second way to render some data is to use computed properties. You use it exactly like a data property. For example:
<
span
id
=
"id3"
style
=
"font-weight: bold;"
>{{ computedProp }}</
span
>
Its definition is different though: the property is defined as a function in the object literal computed of the Vue object. For example:
computed: {
computedProp: function () {
// `this` points to the app instance
return "App startup time: " + this.startupDate +
" - Execution time: " + new Date().toLocaleString() +
" - Dependency: " + this.dependency;
}
},
This produces the following output:
Computed property: App startup time: 5/18/2018, 4:20:42 PM - Execution time: 5/18/2018, 4:20:42 PM - Dependency: I'm dependency property
The second date and time is computed at function execution time. On initial display, the two dates and times are identical because the Vue object creation time and the rendering happened at about the same time.
What is interesting is that a computed property can be executed again if one of its dependencies has changed. This is exactly what happens when we click on the button "Update Dependency." Now we get some output where the two dates and times are different:
Computed property: App startup time: 5/18/2018, 4:20:42 PM - Execution time: 5/18/2018, 4:34:04 PM - Dependency: New value 1 for dependency property
Here is what happens:
- computedProp is dependent on the data property “dependency.”
- When clicking the update button, an event handler changes the value of property “dependency.”
- Vue detects that the “dependency” data property has changed, check its list of dependents for this property and finds computedProp is a dependent. As a consequence it executes the computed property again.
Using Methods
The third way to render some data is to output the result of a function call in a method.
A method is defined in the Vue object in the methods object literal. For example:
methods: {
computedMessageFct:
function
() {
return
new
Date().toLocaleString();
}
}
We use it like this:
<
span
id
=
"id4"
style
=
"font-weight: bold;"
>{{ computedMessageFct() }}</
span
>
Notice the operator () to invoke the function.
When you render the sample page, properties.html, you will notice that span id="id4" gets updated every second. That's weird—we do not make additional calls to this function. Hmm, what's going on?
The reason it is updated every second is that the function computedMessageFct is invoked every time the ui re-renders independently of dependencies. In our case, it's been invoked every second because the clock property is causing a UI update every second. In other words, even though computedMessageFct is not dependent on other properties Vue still considers that span id=”id4” needs to be refreshed, with the result of calling the function another time.
Conclusion
It's important to be aware that a computed property function can be invoked multiple times, and to pay attention to the side effects or performance implications this may have. Luckily for us, the Vue framework caches the results of these function calls and will only invoke the computed property if one of its dependency has changed.
However, this is not the case for methods used for output to HTML elements. They will be invoked again whenever the UI needs re-rendering. So be careful with the kind of computation you do in these functions. We might think we should just use computed properties then and avoid methods, but one of the advantage of methods compared to computed properties is that we can pass parameters. Once aware of the pros and cons of each type, you can choose the path you need for your applications.
And if you're working with Vue, don't forget to check out Kendo UI for Vue, our UI component library that will help you build beautiful Vue apps fast.
Thierry Ciot
Thierry Ciot is a Software Architect on the Corticon Business Rule Management System. Ciot has gained broad experience in the development of products ranging from development tools to production monitoring systems. He is now focusing on bringing Business Rule Management to Javascript and in particular to the serverless world where Corticon will shine. He holds two patents in the memory management space.