We can create Observable objects with MobX. To watch it for changes, we can use the autorun
function.
In this article, we’ll look at how to use the autorun
function to watch for value changes in MobX Observables.
Autorun
mobx.autorun
is used in cases where we want to create a reactive function that doesn’t have an observer itself.
It’s needed for situations like logging, persistence, or UI-updating code.
When autorun
is used, the provided function will always be triggered once immediately and then again each time one of its dependencies changes.
computed
creates functions that only re-evaluate if it has observers on its own. Therefore, autorun
is useful for cases where the Observables don’t have its own observer.
The autorun
function returns a disposer function, which is used to dispose of the autorun when we no longer need it.
The reaction itself will be passed as its only argument of the callback function we pass into autorun
.
Therefore, we can dispose of autorun by writing:
const disposer = autorun(reaction => {});
disposer();
autorun(reaction => {
reaction.dispose();
});
autorun
will only observe data that are used during the execution of the provided function.
For example, we can write the following:
import { autorun, observable, computed } from "mobx";
const numbers = observable([4, 5, 6]);
const sum = computed(() => numbers.reduce((a, b) => a + b, 0));
const disposer = autorun(() => console.log(sum.get()));
numbers.push(7);
to watch the value of sum
, which is a computed value derived from the numbers
Observable array.
Options
The autorun
function takes a variety of options that can be passed in as the properties of an object as the second argument.
They’re the following:
delay
— number of milliseconds that can be used to debounce the callback function. Defaults to 0, which means no delayname
— string that’s used as the name in various situations likespy
eventsonError
— function that’ll handle the errors of the reaction, rather than propagation themscheduler
— set a custom scheduler to determine how re-running autorun should be scheduled. The value is a function that has therun
callback as a parameter like{ scheduler: run => { setTimeout(run, 500) }}
.
onError
We can use onError
as follows:
import { autorun, observable } from "mobx";
const numFruits = observable.box(10);
const dispose = autorun(
() => {
if (numFruits.get() < 0) {
throw new Error("numFruits should not be negative");
}
console.log("Age", numFruits.get());
},
{
onError(e) {
window.alert("Please enter a valid number");
}
}
);
numFruits.set(-1);
dispose();
In the code above, the line:
numFruits.set(-1);
will trigger the ‘Please enter a valid number’ alert to be displayed since we have:
if (numFruits.get() < 0) {
throw new Error("numFruits should not be negative");
}
in the autorun
callback. Therefore, the error will be caught by our onError
handler.
We can also set a global error handler by setting the onReactionError
function.
Conclusion
We can create an Observable and watch its value with the autorun
function. It’s useful for Observables that don’t have an observe
method.
It takes a callback with the reaction
parameter that we can use to call dispose
to dispose of the autorun.
The value of the Observable will be retrieved automatically if we reference it in the callback. As the value of the Observable changes, the autorun
callback will run.
It also takes a variety of options like delay, onError
handler, and more.