browser(firefox): report unhandled rejections for Firefox (#15391)
References #14165
This commit is contained in:
parent
cc45ac91f5
commit
530867e8ab
|
|
@ -1,2 +1,2 @@
|
||||||
1333
|
1334
|
||||||
Changed: lushnikov@chromium.org Tue Jul 5 18:02:39 MSK 2022
|
Changed: lushnikov@chromium.org Wed Jul 6 00:25:34 MSK 2022
|
||||||
|
|
|
||||||
|
|
@ -101,7 +101,6 @@ class PageAgent {
|
||||||
helper.addObserver(this._filePickerShown.bind(this), 'juggler-file-picker-shown'),
|
helper.addObserver(this._filePickerShown.bind(this), 'juggler-file-picker-shown'),
|
||||||
helper.addEventListener(this._messageManager, 'DOMContentLoaded', this._onDOMContentLoaded.bind(this)),
|
helper.addEventListener(this._messageManager, 'DOMContentLoaded', this._onDOMContentLoaded.bind(this)),
|
||||||
helper.addObserver(this._onDocumentOpenLoad.bind(this), 'juggler-document-open-loaded'),
|
helper.addObserver(this._onDocumentOpenLoad.bind(this), 'juggler-document-open-loaded'),
|
||||||
helper.addEventListener(this._messageManager, 'error', this._onError.bind(this)),
|
|
||||||
helper.on(this._frameTree, 'load', this._onLoad.bind(this)),
|
helper.on(this._frameTree, 'load', this._onLoad.bind(this)),
|
||||||
helper.on(this._frameTree, 'frameattached', this._onFrameAttached.bind(this)),
|
helper.on(this._frameTree, 'frameattached', this._onFrameAttached.bind(this)),
|
||||||
helper.on(this._frameTree, 'framedetached', this._onFrameDetached.bind(this)),
|
helper.on(this._frameTree, 'framedetached', this._onFrameDetached.bind(this)),
|
||||||
|
|
@ -129,6 +128,7 @@ class PageAgent {
|
||||||
});
|
});
|
||||||
}),
|
}),
|
||||||
this._runtime.events.onConsoleMessage(msg => this._browserPage.emit('runtimeConsole', msg)),
|
this._runtime.events.onConsoleMessage(msg => this._browserPage.emit('runtimeConsole', msg)),
|
||||||
|
this._runtime.events.onRuntimeError(this._onRuntimeError.bind(this)),
|
||||||
this._runtime.events.onExecutionContextCreated(this._onExecutionContextCreated.bind(this)),
|
this._runtime.events.onExecutionContextCreated(this._onExecutionContextCreated.bind(this)),
|
||||||
this._runtime.events.onExecutionContextDestroyed(this._onExecutionContextDestroyed.bind(this)),
|
this._runtime.events.onExecutionContextDestroyed(this._onExecutionContextDestroyed.bind(this)),
|
||||||
this._runtime.events.onBindingCalled(this._onBindingCalled.bind(this)),
|
this._runtime.events.onBindingCalled(this._onBindingCalled.bind(this)),
|
||||||
|
|
@ -273,15 +273,11 @@ class PageAgent {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
_onError(errorEvent) {
|
_onRuntimeError({ executionContext, message, stack }) {
|
||||||
const docShell = errorEvent.target.ownerGlobal.docShell;
|
|
||||||
const frame = this._frameTree.frameForDocShell(docShell);
|
|
||||||
if (!frame)
|
|
||||||
return;
|
|
||||||
this._browserPage.emit('pageUncaughtError', {
|
this._browserPage.emit('pageUncaughtError', {
|
||||||
frameId: frame.id(),
|
frameId: executionContext.auxData().frameId,
|
||||||
message: errorEvent.message,
|
message: message.toString(),
|
||||||
stack: errorEvent.error && typeof errorEvent.error.stack === 'string' ? errorEvent.error.stack : '',
|
stack: stack.toString(),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -71,6 +71,7 @@ class Runtime {
|
||||||
// Use plain callbacks instead.
|
// Use plain callbacks instead.
|
||||||
this.events = {
|
this.events = {
|
||||||
onConsoleMessage: createEvent(),
|
onConsoleMessage: createEvent(),
|
||||||
|
onRuntimeError: createEvent(),
|
||||||
onErrorFromWorker: createEvent(),
|
onErrorFromWorker: createEvent(),
|
||||||
onExecutionContextCreated: createEvent(),
|
onExecutionContextCreated: createEvent(),
|
||||||
onExecutionContextDestroyed: createEvent(),
|
onExecutionContextDestroyed: createEvent(),
|
||||||
|
|
@ -129,7 +130,7 @@ class Runtime {
|
||||||
|
|
||||||
observe: message => {
|
observe: message => {
|
||||||
if (!(message instanceof Ci.nsIScriptError) || !message.outerWindowID ||
|
if (!(message instanceof Ci.nsIScriptError) || !message.outerWindowID ||
|
||||||
!message.category || disallowedMessageCategories.has(message.category) || message.hasException) {
|
!message.category || disallowedMessageCategories.has(message.category)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const errorWindow = Services.wm.getOuterWindowWithId(message.outerWindowID);
|
const errorWindow = Services.wm.getOuterWindowWithId(message.outerWindowID);
|
||||||
|
|
@ -138,14 +139,16 @@ class Runtime {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const executionContext = this._windowToExecutionContext.get(errorWindow);
|
const executionContext = this._windowToExecutionContext.get(errorWindow);
|
||||||
if (!executionContext)
|
if (!executionContext) {
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
const typeNames = {
|
const typeNames = {
|
||||||
[Ci.nsIConsoleMessage.debug]: 'debug',
|
[Ci.nsIConsoleMessage.debug]: 'debug',
|
||||||
[Ci.nsIConsoleMessage.info]: 'info',
|
[Ci.nsIConsoleMessage.info]: 'info',
|
||||||
[Ci.nsIConsoleMessage.warn]: 'warn',
|
[Ci.nsIConsoleMessage.warn]: 'warn',
|
||||||
[Ci.nsIConsoleMessage.error]: 'error',
|
[Ci.nsIConsoleMessage.error]: 'error',
|
||||||
};
|
};
|
||||||
|
if (!message.hasException) {
|
||||||
emitEvent(this.events.onConsoleMessage, {
|
emitEvent(this.events.onConsoleMessage, {
|
||||||
args: [{
|
args: [{
|
||||||
value: message.message,
|
value: message.message,
|
||||||
|
|
@ -158,6 +161,13 @@ class Runtime {
|
||||||
url: message.sourceName,
|
url: message.sourceName,
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
} else {
|
||||||
|
emitEvent(this.events.onRuntimeError, {
|
||||||
|
executionContext,
|
||||||
|
message: message.errorMessage,
|
||||||
|
stack: message.stack.toString(),
|
||||||
|
});
|
||||||
|
}
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
Services.console.registerListener(consoleServiceListener);
|
Services.console.registerListener(consoleServiceListener);
|
||||||
|
|
|
||||||
|
|
@ -132,3 +132,17 @@ it('should handle window', async ({ page, browserName, isElectron }) => {
|
||||||
it('should remove a listener of a non-existing event handler', async ({ page }) => {
|
it('should remove a listener of a non-existing event handler', async ({ page }) => {
|
||||||
page.removeListener('pageerror', () => {});
|
page.removeListener('pageerror', () => {});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should emit error from unhandled rejects', async ({ page, browserName }) => {
|
||||||
|
it.fixme(browserName === 'firefox', 'see https://github.com/microsoft/playwright/issues/14165');
|
||||||
|
it.info().annotations.push({ type: 'issue', description: 'https://github.com/microsoft/playwright/issues/14165' });
|
||||||
|
const [error] = await Promise.all([
|
||||||
|
page.waitForEvent('pageerror'),
|
||||||
|
page.setContent(`
|
||||||
|
<script>
|
||||||
|
Promise.reject(new Error('sad :('));
|
||||||
|
</script>
|
||||||
|
`),
|
||||||
|
]);
|
||||||
|
expect(error.message).toBe('sad :(');
|
||||||
|
});
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue