diff options
Diffstat (limited to 'spec/frontend/sentry/sentry_config_spec.js')
-rw-r--r-- | spec/frontend/sentry/sentry_config_spec.js | 214 |
1 files changed, 214 insertions, 0 deletions
diff --git a/spec/frontend/sentry/sentry_config_spec.js b/spec/frontend/sentry/sentry_config_spec.js new file mode 100644 index 00000000000..62b8bbd50a2 --- /dev/null +++ b/spec/frontend/sentry/sentry_config_spec.js @@ -0,0 +1,214 @@ +import * as Sentry from '@sentry/browser'; +import SentryConfig from '~/sentry/sentry_config'; + +describe('SentryConfig', () => { + describe('IGNORE_ERRORS', () => { + it('should be an array of strings', () => { + const areStrings = SentryConfig.IGNORE_ERRORS.every(error => typeof error === 'string'); + + expect(areStrings).toBe(true); + }); + }); + + describe('BLACKLIST_URLS', () => { + it('should be an array of regexps', () => { + const areRegExps = SentryConfig.BLACKLIST_URLS.every(url => url instanceof RegExp); + + expect(areRegExps).toBe(true); + }); + }); + + describe('SAMPLE_RATE', () => { + it('should be a finite number', () => { + expect(typeof SentryConfig.SAMPLE_RATE).toEqual('number'); + }); + }); + + describe('init', () => { + const options = { + currentUserId: 1, + }; + + beforeEach(() => { + jest.spyOn(SentryConfig, 'configure'); + jest.spyOn(SentryConfig, 'bindSentryErrors'); + jest.spyOn(SentryConfig, 'setUser'); + + SentryConfig.init(options); + }); + + it('should set the options property', () => { + expect(SentryConfig.options).toEqual(options); + }); + + it('should call the configure method', () => { + expect(SentryConfig.configure).toHaveBeenCalled(); + }); + + it('should call the error bindings method', () => { + expect(SentryConfig.bindSentryErrors).toHaveBeenCalled(); + }); + + it('should call setUser', () => { + expect(SentryConfig.setUser).toHaveBeenCalled(); + }); + + it('should not call setUser if there is no current user ID', () => { + jest.clearAllMocks(); + + options.currentUserId = undefined; + + SentryConfig.init(options); + + expect(SentryConfig.setUser).not.toHaveBeenCalled(); + }); + }); + + describe('configure', () => { + const sentryConfig = {}; + const options = { + dsn: 'https://123@sentry.gitlab.test/123', + whitelistUrls: ['//gitlabUrl', 'webpack-internal://'], + environment: 'test', + release: 'revision', + tags: { + revision: 'revision', + }, + }; + + beforeEach(() => { + jest.spyOn(Sentry, 'init').mockImplementation(); + + sentryConfig.options = options; + sentryConfig.IGNORE_ERRORS = 'ignore_errors'; + sentryConfig.BLACKLIST_URLS = 'blacklist_urls'; + + SentryConfig.configure.call(sentryConfig); + }); + + it('should call Sentry.init', () => { + expect(Sentry.init).toHaveBeenCalledWith({ + dsn: options.dsn, + release: options.release, + tags: options.tags, + sampleRate: 0.95, + whitelistUrls: options.whitelistUrls, + environment: 'test', + ignoreErrors: sentryConfig.IGNORE_ERRORS, + blacklistUrls: sentryConfig.BLACKLIST_URLS, + }); + }); + + it('should set environment from options', () => { + sentryConfig.options.environment = 'development'; + + SentryConfig.configure.call(sentryConfig); + + expect(Sentry.init).toHaveBeenCalledWith({ + dsn: options.dsn, + release: options.release, + tags: options.tags, + sampleRate: 0.95, + whitelistUrls: options.whitelistUrls, + environment: 'development', + ignoreErrors: sentryConfig.IGNORE_ERRORS, + blacklistUrls: sentryConfig.BLACKLIST_URLS, + }); + }); + }); + + describe('setUser', () => { + let sentryConfig; + + beforeEach(() => { + sentryConfig = { options: { currentUserId: 1 } }; + jest.spyOn(Sentry, 'setUser'); + + SentryConfig.setUser.call(sentryConfig); + }); + + it('should call .setUser', () => { + expect(Sentry.setUser).toHaveBeenCalledWith({ + id: sentryConfig.options.currentUserId, + }); + }); + }); + + describe('handleSentryErrors', () => { + let event; + let req; + let config; + let err; + + beforeEach(() => { + event = {}; + req = { status: 'status', responseText: 'Unknown response text', statusText: 'statusText' }; + config = { type: 'type', url: 'url', data: 'data' }; + err = {}; + + jest.spyOn(Sentry, 'captureMessage'); + + SentryConfig.handleSentryErrors(event, req, config, err); + }); + + it('should call Sentry.captureMessage', () => { + expect(Sentry.captureMessage).toHaveBeenCalledWith(err, { + extra: { + type: config.type, + url: config.url, + data: config.data, + status: req.status, + response: req.responseText, + error: err, + event, + }, + }); + }); + + describe('if no err is provided', () => { + beforeEach(() => { + jest.clearAllMocks(); + + SentryConfig.handleSentryErrors(event, req, config); + }); + + it('should use req.statusText as the error value', () => { + expect(Sentry.captureMessage).toHaveBeenCalledWith(req.statusText, { + extra: { + type: config.type, + url: config.url, + data: config.data, + status: req.status, + response: req.responseText, + error: req.statusText, + event, + }, + }); + }); + }); + + describe('if no req.responseText is provided', () => { + beforeEach(() => { + req.responseText = undefined; + + jest.clearAllMocks(); + + SentryConfig.handleSentryErrors(event, req, config, err); + }); + + it('should use `Unknown response text` as the response', () => { + expect(Sentry.captureMessage).toHaveBeenCalledWith(err, { + extra: { + type: config.type, + url: config.url, + data: config.data, + status: req.status, + response: 'Unknown response text', + error: err, + event, + }, + }); + }); + }); + }); +}); |