Skip to content

Instantly share code, notes, and snippets.

@AnalyzePlatypus
Last active June 15, 2021 19:04
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save AnalyzePlatypus/d6be71e966852d28c7cd856df662fcd8 to your computer and use it in GitHub Desktop.
Save AnalyzePlatypus/d6be71e966852d28c7cd856df662fcd8 to your computer and use it in GitHub Desktop.

Vue.js: Use Sentry.io without increasing initial bundle size

There's no questions about it: in the age of "fat" frontend clients, less bloat is better. A useful technique is to split off large libraries into separate Webpack chunks so the they don't take up space in your main bundle, delaying the initial load of your webapp. I like doing this with what I call the "installer pattern". Every split-out library gets its own "installer", an async function that loads the Webpack chunk, performs any initializations or configuration necessary, and then informs the relevant parts of your app that loading has completed.

Here's what that pattern looks like for installing the Sentry.io error reporting SDK:

First, add Sentry to your project:

 yarn add @sentry/browser @sentry/integrations

# Using npm
$ npm install @sentry/browser @sentry/integrations

Next, create a new file exporting an async function that will load Sentry from it's own Webpack chunk:

// installSentry.js

import Vue from 'vue';

const SENTRY_DSN = 'https://*****@sentry.io/****' // Find your DSN on the Sentry Console: https://sentry.io/settings/<team>/projects/<project_id>/keys/

async function installSentry() {
  const Sentry = await import(/* webpackChunkName: 'sentry' */'@sentry/browser');
  const Integrations = await import(/* webpackChunkName: 'sentry' */'@sentry/integrations');
  
  Sentry.init({
    dsn: SENTRY_DSN,
    integrations: [new Integrations.Vue({Vue, attachProps: true, logErrors: true})],
  });  
}

export default installSentry;

Finally, in your main.js, import and call the installer function when in production:

// main.js

import installSentry from "@/installers/installSentry.js";

if(process.env.NODE_ENV === "production") installSentry();

The Sentry SDK now loads in it's own Webpack chuck and does not bloat our main bundle.

@andresespinosapc
Copy link

andresespinosapc commented May 4, 2021

And how do you call Sentry methods? You have a utility method for each Sentry method and import the package in each utility method?

Another question: do you handle errors thrown before Sentry initialization?

@AnalyzePlatypus
Copy link
Author

After Sentry is installed, it's available as window.Sentry.
The Sentry SDK automatically locates and binds to the Vue app.

The trade-off of this approach is that any errors thrown before Sentry is initialized will be missed.
I've found that pre-initialization errors are either critical bugs in the app bootstrapping path (which are easy to catch and fix in testing), or part of the bundle failing to load due to network conditions (which I cannot fix of prevent). So I decide to ignore them.

(In theory, you could build a wrapper around Sentry that saves all errors to a queue, and then drains it into Sentry once initialization is complete)

@andresespinosapc
Copy link

Ok, thanks! Sentry has a lazy loader that saves errors to a queue, but it doesn't enqueue some methods, so I'll have to modify it a bit.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment