Skip to content

Add error message to report #163

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
May 28, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 20 additions & 18 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ Generate, parse and enhance JavaScript stack traces in all browsers

Debug and profile your JavaScript with a [stack trace](http://en.wikipedia.org/wiki/Stack_trace) of function calls leading to an error (or any condition you specify).

stacktrace.js uses browsers' `Error.stack` mechanism to generate stack traces, parses them, enhances them with
[source maps](http://www.html5rocks.com/en/tutorials/developertools/sourcemaps/) and uses
stacktrace.js uses browsers' `Error.stack` mechanism to generate stack traces, parses them, enhances them with
[source maps](http://www.html5rocks.com/en/tutorials/developertools/sourcemaps/) and uses
[Promises](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise)
to return an Array of [StackFrames](https://github.com/stacktracejs/stackframe).

Expand All @@ -16,10 +16,10 @@ to return an Array of [StackFrames](https://github.com/stacktracejs/stackframe).
#### Get a stack trace from current location
```js
var callback = function(stackframes) {
var stringifiedStack = stackframes.map(function(sf) {
return sf.toString();
}).join('\n');
console.log(stringifiedStack);
var stringifiedStack = stackframes.map(function(sf) {
return sf.toString();
}).join('\n');
console.log(stringifiedStack);
};

var errback = function(err) { console.log(err.message); };
Expand All @@ -40,7 +40,7 @@ window.onerror = function(msg, file, line, col, error) {

#### Get stack trace from an Error
```js
var error = new Error('BOOM!');
var error = new Error('BOOM!');

StackTrace.fromError(error).then(callback).catch(errback)
=> Promise(Array[StackFrame], Error)
Expand Down Expand Up @@ -81,48 +81,49 @@ http://cdnjs.com/libraries/stacktrace.js
Generate a backtrace from invocation point, then parse and enhance it.

**(Optional) options: Object**
* *filter: Function([StackFrame](https://github.com/stacktracejs/stackframe) => Boolean)* - Only include stack entries matching for which `filter` returns `true`
* *filter: Function([StackFrame](https://github.com/stacktracejs/stackframe) => Boolean)* - Only include stack entries matching for which `filter` returns `true`
* *sourceCache: Object (String URL => String Source)* - Pre-populate source cache to avoid network requests
* *offline: Boolean (default: false)* - Set to `true` to prevent all network requests

#### `StackTrace.fromError(error, /*optional*/ options)` => [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise)(Array[[StackFrame](https://github.com/stacktracejs/stackframe)])
Given an Error object, use [error-stack-parser](https://github.com/stacktracejs/error-stack-parser)
to parse it and enhance location information with [stacktrace-gps](https://github.com/stacktracejs/stacktrace-gps).

**error: Error**

**(Optional) options: Object**
* *filter: Function([StackFrame](https://github.com/stacktracejs/stackframe) => Boolean)* - Only include stack entries matching for which `filter` returns `true`
* *sourceCache: Object (String URL => String Source)* - Pre-populate source cache to avoid network requests
* *offline: Boolean (default: false)* - Set to `true` to prevent all network requests

#### `StackTrace.generateArtificially(/*optional*/ options)` => [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise)(Array[[StackFrame](https://github.com/stacktracejs/stackframe)])
Use [stack-generator](https://github.com/stacktracejs/stack-generator) to generate a backtrace by walking the `arguments.callee.caller` chain.

**(Optional) options: Object**
* *filter: Function([StackFrame](https://github.com/stacktracejs/stackframe) => Boolean)* - Only include stack entries matching for which `filter` returns `true`
* *sourceCache: Object (String URL => String Source)* - Pre-populate source cache to avoid network requests
* *offline: Boolean (default: false)* - Set to `true` to prevent all network requests

#### `StackTrace.instrument(fn, callback, /*optional*/ errback)` => Function
* Given a function, wrap it such that invocations trigger a callback that is called with a stack trace.

* **fn: Function** - to wrap, call callback on invocation and call-through
* **callback: Function** - to call with stack trace (generated by `StackTrace.get()`) when fn is called
* **(Optional) errback: Function** - to call with Error object if there was a problem getting a stack trace.
* **(Optional) errback: Function** - to call with Error object if there was a problem getting a stack trace.
Fails silently (though `fn` is still called) if a stack trace couldn't be generated.

#### `StackTrace.deinstrument(fn)` => Function
Given a function that has been instrumented, revert the function to it's original (non-instrumented) state.

* **fn: Function** - Instrumented Function

#### `StackTrace.report(stackframes, url)` => [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise)(String)
Given an Array of StackFrames, serialize and POST to given URL. Promise is resolved with response text from POST request.
#### `StackTrace.report(stackframes, url, message)` => [Promise](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise)(String)
Given an an error message and Array of StackFrames, serialize and POST to given URL. Promise is resolved with response text from POST request.

Example JSON POST data:
```
{
message: 'BOOM',
stack: [
{functionName: 'fn', fileName: 'file.js', lineNumber: 32, columnNumber: 1},
{functionName: 'fn2', fileName: 'file.js', lineNumber: 543, columnNumber: 32},
Expand All @@ -131,6 +132,7 @@ Example JSON POST data:
}
```

* **message: String** - The error message
* **stackframes: Array([StackFrame](https://github.com/stacktracejs/stackframe))** - Previously wrapped Function
* **url: String** - URL to POST stack JSON to

Expand All @@ -140,8 +142,8 @@ Example JSON POST data:
> **HEADS UP**: You won't get the benefit of [source maps](http://www.html5rocks.com/en/tutorials/developertools/sourcemaps/)
in IE9- or other very old browsers.

## Using node.js/io.js only?
I recommend the [stack-trace node package](https://www.npmjs.com/package/stack-trace) specifically built for node.
## Using node.js/io.js only?
I recommend the [stack-trace node package](https://www.npmjs.com/package/stack-trace) specifically built for node.
It has a very similar API and also supports source maps.

## Contributing
Expand Down
20 changes: 19 additions & 1 deletion spec/stacktrace-spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -192,7 +192,25 @@ describe('StackTrace', function() {
jasmine.Ajax.uninstall();
});

it('sends POST request to given URL', function(done) {
it('sends POST request to given URL with a message', function(done) {
var url = 'http://domain.ext/endpoint';
var errorMsg = 'BOOM';
var stackframes = [new StackFrame('fn', undefined, 'file.js', 32, 1)];

StackTrace.report(stackframes, url, errorMsg).then(callback, done.fail)['catch'](done.fail);

var postRequest = jasmine.Ajax.requests.mostRecent();
postRequest.respondWith({status: 201, contentType: 'text/plain', responseText: 'OK'});

function callback() {
expect(postRequest.data()).toEqual({message: errorMsg, stack: stackframes});
expect(postRequest.method).toBe('post');
expect(postRequest.url).toBe(url);
done();
}
});

it('sends POST request to given URL without a message', function(done) {
var url = 'http://domain.ext/endpoint';
var stackframes = [new StackFrame('fn', undefined, 'file.js', 32, 1)];

Expand Down
13 changes: 10 additions & 3 deletions stacktrace.js
Original file line number Diff line number Diff line change
Expand Up @@ -163,12 +163,13 @@
},

/**
* Given an Array of StackFrames, serialize and POST to given URL.
* Given an error message and Array of StackFrames, serialize and POST to given URL.
*
* @param {Array} stackframes
* @param {String} url
* @param {String} errorMsg
*/
report: function StackTrace$$report(stackframes, url) {
report: function StackTrace$$report(stackframes, url, errorMsg) {
return new Promise(function(resolve, reject) {
var req = new XMLHttpRequest();
req.onerror = reject;
Expand All @@ -183,7 +184,13 @@
};
req.open('post', url);
req.setRequestHeader('Content-Type', 'application/json');
req.send(JSON.stringify({stack: stackframes}));

var reportPayload = {stack: stackframes};
if (errorMsg != undefined) {
reportPayload.message = errorMsg;
}

req.send(JSON.stringify(reportPayload));
});
}
};
Expand Down