Error/Exception handling in Vue.js application
Architecting a large scale frontend application is not as simple as it used to be. Now, applications are more complex and dynamic. Thats why, we have to consider a lots of parameters while architecting a frontend application and error/exception handling is one of important aspect. Having a good error handling mechanism in the application come up with a lot of benefits such as:
- A good error handling mechanism prevents the application from breaking when there is an unhandled exception
- Errors can be easily logged to a server to track down the causes in case of production application
- Can perform the alternate operations such as displaying an alternate UI showing some sophisticated messages instead of breaking the application
- Helps in improving the user experience
This article is 4th part of the series Architect a large scale Vue.js Application . You can find the supporting boilerplate here.
In a frontend application, the most common types of errors/exceptions could be:
- Syntax errors — Because of using some wrong syntax
- Runtime errors— Due to an illegal operation during execution
- Logical errors — As a result of mistake in the program logic
- Http errors — APIs returning some errors
There are numerous ways to tackle these problems such as syntax error can be discovered at compile time using static type checking(TypeScript)
, runtime errors can be handled using proper try-catch
statements, logical errors can be reduced by having proper unit/integration
testing, http errors can be handled by using promises
.
In this article, I am going to explain, how should we implement the proper error/exception handling mechanism in Vue.js applications.
Vue.js implement its own way to deal with the errors/exceptions. In general, there are 2 different ways to handle the errors in Vue.js application
- Using Vue.js global configuration
- Using
ErrorBoundaries
orerrorCaptured
lifecycle hook
Using Vue.js global configuration:
Vue.js has a global Vue.config
object which contains the global configurations for the application such as suppress logs and warnings, devtools, error handler etc.
We can override these configurations with our own configurations. For error handling, we can assign a handler function to Vue.config.errorHandler
. The handler
gets called for any uncaught exceptions within any Vue instance (Vue components) throughout the application. It acts like a global error handler for Vue.js application. The following code snippets shows the registration of handler function
:
The handler contains 3 parameters:
- err: complete error trace, contains the
message
anderror stack
- vm: Vue component/instance in which error is occurred
- info: Vue specific error information such as lifecycle hooks, events etc.
Vue.config.errorHandler
captures the errors that are specific to Vue instances. It would not be able to capture the errors which are outside of Vue instances such as utils files, services etc.
To capture the errors, which are outside of Vue instances, window’s onerror
event can be used. We can register a handler function
which will capture all the unhandled exceptions which are not specific to Vue instances. The following code snippets shows the registration of onerror
handler.
Using ErrorBoundaries or errorCaptured lifecycle hook:
Vue.js introduced a new lifecycle hook method errorCaptured
in 2.5.0
. This lifecycle hook provides a way to deal component specific error within the component itself. Although, this opens a way to create some error boundaries with in the Vue.js application.
The errorCaptured
hook has the same signature as global errorHandler
i.e it has 3 parameters (err, vm, info)
as shown below:
Error boundaries are the another form of using errorCaptured
lifecycle hook. These are reusable component which will have the implementation of errorCaptured
and the error boundary component can compose another components just to create the error boundaries around them. Error boundaries are responsible for capturing the unhandled errors/exceptions within its child components tree, logs those errors or display a fallback UI. Following code snippets shows error boundary component and its usage.
Any uncaught error/exception within the app-user-item
component will be handled by error-boundary
component.
If the complete application is composed within the
error-boundary
, then it will behave like globalerrorHandler
.By default, error captured by the
errorCaptured
lifecycle hooks will propagate to its parents and then finally to global error handler(config.errorHandler)
but this propagation can be stopped by returningfalse
from theerrorCaptured
method.
I prepared the boilerplate around this architecture. You can find it here https://github.com/arunredhu/vuejs_boilerplate. I look forward to see your contribution.
Conclusion:
Error handling is very important for an enterprise application. In this article, we talked about the global error handler using config.errorHandler
and component local error handler using lifecycle hook errorCaptured
. This solution provides the basic details with the help of which you can easily implement error handling for an application and log them. This will help you create a better user experience.