Skip to content

Commit 99cf147

Browse files
committed
Breadcrumb capturing should not end up in stack trace
1 parent c3e847c commit 99cf147

File tree

1 file changed

+21
-36
lines changed

1 file changed

+21
-36
lines changed

src/raven.js

Lines changed: 21 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -204,9 +204,10 @@ Raven.prototype = {
204204
*
205205
* @param {object} options A specific set of options for this context [optional]
206206
* @param {function} func The function to be wrapped in a new context
207+
* @param {function} func A function to call before the try/catch wrapper [optional, private]
207208
* @return {function} The newly wrapped functions with a context
208209
*/
209-
wrap: function(options, func) {
210+
wrap: function(options, func, _before) {
210211
var self = this;
211212
// 1 argument has been passed, and it's not a function
212213
// so just return it
@@ -246,9 +247,13 @@ Raven.prototype = {
246247
function wrapped() {
247248
var args = [], i = arguments.length,
248249
deep = !options || options && options.deep !== false;
250+
251+
if (_before && isFunction(_before)) {
252+
_before.apply(this, arguments);
253+
}
254+
249255
// Recursively wrap all of a function's arguments that are
250256
// functions themselves.
251-
252257
while(i--) args[i] = deep ? self.wrap(options, arguments[i]) : arguments[i];
253258

254259
try {
@@ -260,29 +265,20 @@ Raven.prototype = {
260265
}
261266
}
262267

263-
this._imitate(wrapped, func);
264-
265-
func.__raven_wrapper__ = wrapped;
266-
// Signal that this function has been wrapped already
267-
// for both debugging and to prevent it to being wrapped twice
268-
wrapped.__raven__ = true;
269-
wrapped.__inner__ = func;
270-
271-
return wrapped;
272-
},
273-
274-
/**
275-
* Give a wrapper function the properties/prototype
276-
* of the wrapepd (inner) function
277-
*/
278-
_imitate: function (wrapped, func) {
279268
// copy over properties of the old function
280269
for (var property in func) {
281270
if (hasKey(func, property)) {
282271
wrapped[property] = func[property];
283272
}
284273
}
285274
wrapped.prototype = func.prototype;
275+
276+
func.__raven_wrapper__ = wrapped;
277+
// Signal that this function has been wrapped already
278+
// for both debugging and to prevent it to being wrapped twice
279+
wrapped.__raven__ = true;
280+
wrapped.__inner__ = func;
281+
286282
return wrapped;
287283
},
288284

@@ -624,9 +620,9 @@ Raven.prototype = {
624620
* @returns {Function}
625621
* @private
626622
*/
627-
_wrapEventHandlerForBreadcrumbs: function(evtName, fn) {
623+
_breadcrumbEventHandler: function(evtName) {
628624
var self = this;
629-
function wrapped(evt) {
625+
return function (evt) {
630626
// It's possible this handler might trigger multiple times for the same
631627
// event (e.g. event propagation through node ancestors). Ignore if we've
632628
// already captured the event.
@@ -642,16 +638,7 @@ Raven.prototype = {
642638
target: htmlElementAsString(elem)
643639
}
644640
});
645-
if (fn) return fn.apply(this, arguments);
646641
};
647-
648-
if (fn) {
649-
this._imitate(wrapped, fn);
650-
fn.__raven_breadcrumb__ = wrapped;
651-
652-
}
653-
654-
return wrapped;
655642
},
656643

657644
/**
@@ -701,7 +688,7 @@ Raven.prototype = {
701688
// Capture breadcrubms from any click that is unhandled / bubbled up all the way
702689
// to the document. Do this before we instrument addEventListener.
703690
if (this._hasDocument) {
704-
document.addEventListener('click', self._wrapEventHandlerForBreadcrumbs('click'));
691+
document.addEventListener('click', self._breadcrumbEventHandler('click'));
705692

706693
}
707694

@@ -720,19 +707,17 @@ Raven.prototype = {
720707
// can sometimes get 'Permission denied to access property "handle Event'
721708
}
722709

710+
723711
// TODO: more than just click
712+
var before;
724713
if ((global === 'EventTarget' || global === 'Node') && evt === 'click') {
725-
fn = self._wrapEventHandlerForBreadcrumbs(evt, fn);
714+
before = self._breadcrumbEventHandler(evt, fn);
726715
}
727-
return orig.call(this, evt, self.wrap(fn), capture, secure);
716+
return orig.call(this, evt, self.wrap(fn, undefined, before), capture, secure);
728717
};
729718
});
730719
fill(proto, 'removeEventListener', function (orig) {
731720
return function (evt, fn, capture, secure) {
732-
// from the original function, get the breadcrumb wrapper
733-
// from the breadcrumb wrapper, get the raven wrapper (try/catch)
734-
// i.e. fn => breadcrumb_wrapper(fn) => raven_wrapper(breadcrumb_wrapper(fn))
735-
fn = fn && (fn.__raven_breadcrumb__ ? fn.__raven_breadcrumb__ : fn);
736721
fn = fn && (fn.__raven_wrapper__ ? fn.__raven_wrapper__ : fn);
737722
return orig.call(this, evt, fn, capture, secure);
738723
};

0 commit comments

Comments
 (0)