Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings
This repository was archived by the owner on Apr 12, 2024. It is now read-only.
/angular.jsPublic archive

Add traceback to unhandled promise rejections, Fixes: #14631#15527

Closed
graingert wants to merge1 commit intoangular:masterfromgraingert:patch-3

Conversation

graingert
Copy link
Contributor

@graingertgraingert commentedDec 19, 2016
edited
Loading

What kind of change does this PR introduce? (Bug fix, feature, docs update, ...)
Feature

What is the current behavior? (You can also link to an open issue here)
Console is filled with meaningless:Possibly unhandled rejection: {} errors

What is the new behavior (if this is a feature change)?
Console is filled with juicy traceback info.

Does this PR introduce a breaking change?
I don't think so

Please check if the PR fulfills these requirements

Other information:

@graingert
Copy link
ContributorAuthor

@gkalpak uhh, are the tests for the unhandled rejection even run? I added these to intentionally fail...

@gkalpak
Copy link
Member

gkalpak commentedDec 20, 2016
edited
Loading

Not sure what you mean. The tests should run (and I am quite sure they do).
(The tests need some fixes, because they are not currently testing what they should be testing, but that is unrelated.)

@graingert
Copy link
ContributorAuthor

@gkalpakhttps://github.com/angular/angular.js/pull/15527/files#diff-0cfb390955e411a4a5437fa337d52481R2181 should fail on the fixture.type === 'exception' because it doesn't stringify to 'foo'.

@graingert
Copy link
ContributorAuthor

@gkalpak are you in IRC?

@gkalpak
Copy link
Member

gkalpak commentedDec 20, 2016
edited
Loading

@graingert, if you want it to fail, then you betternot reject the promise withfoo 😛
(I am rarely (read "never") on IRC these days, but you can find me on gitter.)

@graingert
Copy link
ContributorAuthor

@gkalpak oh I am a silly... Fixing...

@gkalpak
Copy link
Member

BTW, it would made our life a tiny bit easier if you followed ourcommit message guidelines 😉

@graingert
Copy link
ContributorAuthor

@gkalpak will do once I've got the tests working. Also your URL is out of date: you wanthttps://github.com/angular/angular.js/blob/master/CONTRIBUTING.md#commit-message-format

@@ -381,7 +381,11 @@ function qFactory(nextTick, exceptionHandler, errorOnUnhandledRejections) {
if (!toCheck.pur) {
toCheck.pur = true;
var errorMessage = 'Possibly unhandled rejection: ' + toDebugString(toCheck.value);
Copy link
Member

@gkalpakgkalpakDec 20, 2016
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Here is another idea (either fortoDebugString() or just here):
IftoCheck.value has atoString() method that is not the defaultObject.prototype.toString(), then use that for serializing it. Something similar tostringify.

@graingertgraingertforce-pushed thepatch-3 branch 2 times, most recently from6e2531b to013779cCompareDecember 20, 2016 12:58
@gkalpak
Copy link
Member

Thx! (My URL was fine btw - just intentionally pointing to the supersection of yours 😛)

@graingert
Copy link
ContributorAuthor

graingert commentedDec 20, 2016
edited
Loading

@gkalpak ah it didn't go to a section for me at all. (it works now)

gkalpak reacted with confused emoji

@graingertgraingertforce-pushed thepatch-3 branch 5 times, most recently fromc014f10 to1654b47CompareDecember 20, 2016 15:28
@graingert
Copy link
ContributorAuthor

@gkalpak and we're green!

@gkalpak
Copy link
Member

@graingert, awesome! Now on to that commit message 😛

Copy link
Member

@gkalpakgkalpak left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

I left some comments, but the general idea LGTM.

var exceptionStr = toDebugString(exceptionEg);
var fixtures = [
{
type: 'exception',
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Change "exception" to "Error object".

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Cool

var type = fixture.type;
var value = fixture.value;
var expected = fixture.expected;
it('should log an unhandled' + type + ' rejected promise', function() {
Copy link
Member

@gkalpakgkalpakDec 20, 2016
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Instead of repeatingtype in allit blocks, create adescribe block for each fixture and puttype in its description.

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Ah makes sense

forEach(fixtures, function(fixture) {
var type = fixture.type;
var value = fixture.value;
var expected = fixture.expected;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Extra points for putting some space beforeit blocks 😃

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Ordescribe blocks...

expected: {
reason: 'Possibly unhandled rejection: foo'
}
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

A couple more fixtures would be in order imo. E.g.:

  • One with a non-Error object.
  • One with an object that "extends"Error.

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Yeah makes sense

@graingert
Copy link
ContributorAuthor

@gkalpak done

Copy link
Member

@gkalpakgkalpak left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

A couple of nitpicks, but otherwise LGTM.

}
},
{
type: 'plain value',
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Now everyone is capitalized except forplain value. Just because it is nothing more than a plain value, doesn't mean you have to treat it like a 2nd-class citizen 😛

Copy link
ContributorAuthor

@graingertgraingertDec 21, 2016
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

I went with all lower case, and more accurate names

forEach(fixtures, function(fixture) {
var type = fixture.type;
var value = fixture.value;
var expected = fixture.expected;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Ordescribe blocks...

var type = fixture.type;
var value = fixture.value;
var expected = fixture.expected;
describe(type, function() {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Nit: Using something like'with ' + type will make the description read better (in case of an error for example).

mgol reacted with thumbs up emoji
@graingert
Copy link
ContributorAuthor

@gkalpak done

Copy link
Member

@gkalpakgkalpak left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

LGTM, but let's wait for some feedback from others as well.
(In the mean time, feel free to fix up that commit message 😁)

@graingert
Copy link
ContributorAuthor

@gkalpak I did fix the commit message... What's wrong with it?

@gkalpak
Copy link
Member

gkalpak commentedDec 21, 2016
edited
Loading

Actual:

fix($q): Add traceback to unhandled promise rejections, Fixes:#14631

Expected something like:

fix($q): add traceback to unhandled promise rejections

Fixes#14631

(The change may seem trivial, but the format is important, because we auto-generate the changelog from these commit messages. So small deviations can make a lot of difference in the resulting changelog.)

@mgol
Copy link
Member

@graingert Thanks for the PR, this is awesome. 👏

I don't have any remarks apart from the incorrect commit message format.

@graingert
Copy link
ContributorAuthor

@gkalpak commit message fixed

@@ -381,7 +381,11 @@ function qFactory(nextTick, exceptionHandler, errorOnUnhandledRejections) {
if (!toCheck.pur) {
toCheck.pur = true;
var errorMessage = 'Possibly unhandled rejection: ' + toDebugString(toCheck.value);
exceptionHandler(errorMessage);
if (toCheck.value instanceof Error) {
exceptionHandler(toCheck.value, errorMessage);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Is this the correct order? It looks weird when the error message isafter the stack trace.

Copy link
ContributorAuthor

@graingertgraingertDec 21, 2016
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Fromhttps://docs.angularjs.org/api/ng/service/$exceptionHandler

$exceptionHandler(exception,[cause]);
ParamTypeDetails
exceptionErrorException associated with the error.
cause(optional)stringOptional information...

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Hmm, OK. I mostly wondered because this:
screen shot 2016-12-21 at 15 48 43
looks a little weird.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

There is nothing in the$exceptionHandler code that would make the order important; that's all of it:

function$ExceptionHandlerProvider(){this.$get=['$log',function($log){returnfunction(exception,cause){$log.error.apply($log,arguments);};}];}

I wonder what's the reason for the current documentation.@gkalpak,@petebacondarwin does any one of you know?

Copy link
ContributorAuthor

@graingertgraingertDec 21, 2016
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

what about just doing

exceptionHandler(toCheck.value,'Possibly unhandled rejection')

with no ifs or errorMessage generation.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

That sounds sensible but I'd still swap the order of operations. Note that currently we are trying to show the'Possibly unhandled rejection' message first and the error afterwards; we just put it all in one string argument so the stack trace gets lost. So I'd like:

exceptionHandler('Possibly unhandled rejection',toCheck.value);

but that would require updating the docs to no longer require the cause to be the second parameter (no code changes required as it already works as I mentioned before).

I'd just want to know if there's any reason for the current signature so let's see what others say. :)

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

@mgol my custom $exceptionHandlers are configured to pass the first argument as the Error value, as per the documentation.

I presume others follow the same documentation also.

Copy link
Member

@mgolmgolDec 21, 2016
edited
Loading

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

@graingert Is the issue that some automated tools might only pick up the first argument and discard others, losing the error context? Because otherwise, in Angular source, the order influences only one thing - the order in which messages/errors are logged. And it makes more sense to log the summary first and the error second. In other words, the following:

exceptionHandler('Possibly unhandled rejection',toCheck.value);

is analogous to:

exceptionHandler('Possibly unhandled rejection: '+toDebugString(toCheck.value));

just with more details printed to the console as the error stack is not lost.

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

@mgol swapping the types of the parameters of $exceptionHandler is another issue for another PR, and would be a breaking change.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

OK, fair enough. In that case, maybe it's better to leave it as it is for now; your proposal to just write:

exceptionHandler(toCheck.value,'Possibly unhandled rejection');

sounds nice but we pass other data types throughtoDebugString and we'd lose it in that case. If we want to tweak that, it would be better to tackle that separately after this PR lands.

@@ -381,7 +381,11 @@ function qFactory(nextTick, exceptionHandler, errorOnUnhandledRejections) {
if (!toCheck.pur) {
toCheck.pur = true;
var errorMessage = 'Possibly unhandled rejection: ' + toDebugString(toCheck.value);
exceptionHandler(errorMessage);
if (toCheck.value instanceof Error) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Though I don't think it necessarily a concern here, do we care that this will not identify errors that originate from an iframe? Don't know how common of a use case that is.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

I doubt it's common but if it turns out to be an issue we can revisit.

Ideally we would convert to a string (viatoDebugString) only certain types of values and log others unchanged. The problem is that then we'd have to passPossibly unhandled rejection andtoCheck.value as separate arguments to$exceptionHandler and if we do it in a documented way (error first, (optional) reason second) the message would get swapped from e.g.:

'Possibly unhandled rejection: MY_THING'

to:

'MY_THING' 'Possibly unhandled rejection'

which is less pleasant.

We can discuss it but let's do it in a separate issue if desired.

mgol pushed a commit that referenced this pull requestDec 21, 2016
@mgol
Copy link
Member

Landed, thanks!

@mgol
Copy link
Member

@graingert One nit (I fixed it myself): there should be no colon afterFixes in the commit description.

Sign up for freeto subscribe to this conversation on GitHub. Already have an account?Sign in.
Reviewers

@dchermandchermandcherman left review comments

@mgolmgolmgol approved these changes

@gkalpakgkalpakgkalpak approved these changes

Assignees
No one assigned
Projects
None yet
Milestone
1.6.x
Development

Successfully merging this pull request may close these issues.

5 participants
@graingert@gkalpak@mgol@dcherman@googlebot

[8]ページ先頭

©2009-2025 Movatter.jp