A deep dive in the Vue.js source code (#11): the warn function

If you are just joining, this is the 11th post in a series going over the entire Vue.js source code line by line. In this post, we look at the warn function:

The warn function

By default, the warn function does nothing:

function noop (a, b, c) {}
[. . . .]
var warn = noop;

But if you are in a development environment, the warn function does something:

if (process.env.NODE_ENV !== 'production') {
var hasConsole = typeof console !== 'undefined';
[. . . .]
  warn = function (msg, vm) {
var trace = vm ? generateComponentTrace(vm) : '';
  if (config.warnHandler) {
config.warnHandler.call(null, msg, vm, trace);
} else if (hasConsole && (!config.silent)) {
console.error(("[Vue warn]: " + msg + trace));
}
};
[. . . .]
}

But what does it do?

The warn function takes two parameters:

warn = function (msg, vm) {
[. . . .]
}

The msg parameter is a string, and the vm parameter is a Vue instance. For example:

warn(
'Failed to mount component: template or render function not defined.', vm
);

The warn function initializes a variable trace:

var trace = vm ? generateComponentTrace(vm) : '';

If a vm parameter is passed to warn, trace is set to the result of calling generateComponentTrace and passing vm as a parameter:

var trace = vm ? generateComponentTrace(vm) : '';

If a vm parameter is not passed to warn, trace is set to an empty string:

var trace = vm ? generateComponentTrace(vm) : '';

Let’s save the discussion ofgenerateComponentTrace for next time.

The warn function then checks whether aconfig.warnHandler has been set:

if (config.warnHandler) {
config.warnHandler.call(null, msg, vm, trace);
} else if (hasConsole && (!config.silent)) {
console.error(("[Vue warn]: " + msg + trace));
}

According to the Vue.js API, config.warnHandler assigns “a custom handler for runtime Vue warnings. Note this only works during development and is ignored in production.” The API describes its usage as follows:

Vue.config.warnHandler = function (msg, vm, trace) {
// `trace` is the component hierarchy trace
}

As you can see, Vue.config.warnHandler is a function. The function takes a message , a Vue instance, and trace as parameters and allows you to customize warning handling within the body of the function.

Now, let’s turn back to the warn function. If a Vue.config.warnHandler has been set, the warn function uses the .call() method to call config.warnHandler:

config.warnHandler.call(null, msg, vm, trace);

The .call() method receives null as the the value of this and takes three parameters: (1) a message, (2) a Vue Instance, and (3) trace:

config.warnHandler.call(null, msg, vm, trace);

On the other hand, if config.warnHandler has not been set, the warn function moves on to check some other conditions:

} else if (hasConsole && (!config.silent)) {
console.error(("[Vue warn]: " + msg + trace));
}

First, warn checks whether hasConsole is true:

} else if (hasConsole && (!config.silent)) {

Would it surprise you to learn that hasConsole checks whether the environment has a console?

var hasConsole = typeof console !== 'undefined';

Next, warn checks whether config.silent is not true:

} else if (hasConsole && (!config.silent)) {

If these conditions are met, warn calls console.error:

console.error(("[Vue warn]: " + msg + trace));

console.error “outputs an error message to the web console.” Here, console.error outputs “[Vue warn]: “ and concatenates msg and trace. msg comes from the parameter passed to the warn function. trace is set within the warn function, as described in more detail above.

Recap

To recap, in development mode the warn function takes a string and Vue instance as parameters and then either calls a custom warning handler or a default console.error error handler to warn you of an issue. The default handler provides a warning message and trace.

Next Post

In the next post, we will take a look at the generateComponentTrace function.