Tips and Tricks

These are some general recommendations and tips for how to get the most out of Raven.js and Sentry.

The first thing to do is to consider limiting exceptions to those raised from a list of allowed domains.

If your scripts are loaded from cdn.example.com and your site is example.com it’d be reasonable to set whitelistUrls to:

Copied
whitelistUrls: [/https?:\/\/((cdn|www)\.)?example\.com/];

Since this accepts a regular expression, that would catch anything *.example.com or example.com exactly. See also: Config: whitelistUrls.

Next, check out the list of integrations we provide and see which are applicable to you.

The community has compiled a list of common ignore rules for common things, like Facebook, Chrome extensions, etc. So it’s recommended to at least check these out and see if they apply to you. Check out the original gist.

Copied
const sentryOptions = {
  ignoreErrors: [
    // Random plugins/extensions
    "top.GLOBALS",
    // See: http://blog.errorception.com/2012/03/tale-of-unfindable-js-error.html
    "originalCreateNotification",
    "canvas.contentDocument",
    "MyApp_RemoveAllHighlights",
    "http://tt.epicplay.com",
    "Can't find variable: ZiteReader",
    "jigsaw is not defined",
    "ComboSearch is not defined",
    "http://loading.retry.widdit.com/",
    "atomicFindClose",
    // Facebook borked
    "fb_xd_fragment",
    // ISP "optimizing" proxy - `Cache-Control: no-transform` seems to reduce this. (thanks @acdha)
    // See http://stackoverflow.com/questions/4113268/how-to-stop-javascript-injection-from-vodafone-proxy
    "bmi_SafeAddOnload",
    "EBCallBackMessageReceived",
    // See http://toolbar.conduit.com/Developer/HtmlAndGadget/Methods/JSInjection.aspx
    "conduitPage",
    // Generic error code from errors outside the security sandbox
    // You can delete this if using raven.js > 1.0, which ignores these automatically.
    "Script error.",
    // Avast extension error
    "_avast_submit",
  ],
  denyUrls: [
    // Google Adsense
    /pagead\/js/i,
    // Facebook flakiness
    /graph\.facebook\.com/i,
    // Facebook blocked
    /connect\.facebook\.net\/en_US\/all\.js/i,
    // Woopra flakiness
    /eatdifferent\.com\.woopra-ns\.com/i,
    /static\.woopra\.com\/js\/woopra\.js/i,
    // Chrome extensions
    /extensions\//i,
    /^chrome:\/\//i,
    /^chrome-extension:\/\//i,
    // Other plugins
    /127\.0\.0\.1:4001\/isrunning/i, // Cacaoweb
    /webappstoolbarba\.texthelp\.com\//i,
    /metrics\.itunes\.apple\.com\.edgesuite\.net\//i,
  ],
};

It happens frequently that errors sent from your frontend can be overwhelming. One solution here is to only send a sample of the events that happen. You can do this via the shouldSendCallback setting:

Copied
shouldSendCallback: function(data) {
    // only send 10% of errors
    var sampleRate = 10;
    return (Math.random() * 100 <= sampleRate);
}

For automatically reporting AJAX errors from jQuery, the following tips might be helpful, however depending on the type of request you might have to do slightly different things.

Whenever an Ajax request completes with an error, jQuery triggers the ajaxError event, passing the event object, the jqXHR object (prior to jQuery 1.5, the XHR object), and the settings object that was used in the creation of the request. When an HTTP error occurs, the fourth argument (thrownError) receives the textual portion of the HTTP status, such as “Not Found” or “Internal Server Error.”

You can use this event to globally handle Ajax errors:

Copied
$(document).ajaxError(function (event, jqXHR, ajaxSettings, thrownError) {
  Raven.captureMessage(thrownError || jqXHR.statusText, {
    extra: {
      type: ajaxSettings.type,
      url: ajaxSettings.url,
      data: ajaxSettings.data,
      status: jqXHR.status,
      error: thrownError || jqXHR.statusText,
      response: jqXHR.responseText.substring(0, 100),
    },
  });
});

Due to security reasons most web browsers are not giving permissions to access error messages for cross domain scripts. This is not jQuery issue but an overall JavaScript limitation.

Depending on your situation you have different options now:

If you have access to the backend system you are calling, you can set response headers to allow a cross domain call:

Copied
Access-Control-Allow-Origin: *

Script tags have now got a new non-standard attribute called crossorigin (read more). The most secure value for this would be anonymous. So, you’ll have to modify your script tags to look like the following:

Copied
<script
  src="http://sub.domain.com/script.js"
  crossorigin="anonymous"
></script>

If you have no access to the backend, you could try a workaround, which is basically adding a timeout on the Ajax call. This is however very dirty, and will fail on slow connection or long response time:

Copied
$.ajax({
    url: 'http://mysite/leaflet.js',
    success: function() { ... },
    error: function() { ... },
    timeout: 2000, // 2 seconds timeout before error function will be called
    dataType: 'script',
    crossDomain: true
});

When building tests for your application, you want to assert that the right flow-tracking or error is being sent to Sentry, but without really sending it to the Sentry system. This way you won’t swamp it with false reports during test running and other CI operations.

Raven Test Kit enables Raven to work natively in your application, but it overrides the default Raven transport mechanism so the report is not really sent but rather logged locally. In this way, the logged reports can be fetched later for usage verification or other uses you may have in your testing environment.

Copied
npm install raven-testkit --save-dev

Then you may create a testkit instance and validate your reports against it as follows:

Copied
import testKitInitializer from "raven-testkit";

const testKit = testKitInitializer(Raven);

// any scenario that should call Raven.catchException(...)

expect(testKit.reports()).to.have.lengthOf(1);
const report = testKit.reports()[0];
expect(report).to.have.property("release").to.equal("test");

Additionally, you may pass your own shouldSendCallback logic

Copied
const shouldSendCallback = (data) => {
  return; /* your own logic */
};
const testKit = testKitInitializer(Raven, shouldSendCallback);

Other useful API, more example usage and updates can be found in Raven Test Kit

Help improve this content
Our documentation is open source and available on GitHub. Your contributions are welcome, whether fixing a typo (drat!) or suggesting an update ("yeah, this would be better").