CodeceptJS
CodeceptJS copied to clipboard
"Error: Execution context was destroyed" happens on the page which uses meta tag refresh
What are you trying to achieve?
I'm now testing the pages which has meta tag refresh. (You can see the detail on the code below.)
What do you get instead?
Every time I get "Error: Execution context was destroyed" when meta tag refresh happens.
Provide console output if related. Use
--verbosemode for more details.
$ ./node_modules/.bin/codeceptjs run --steps --verbose
CodeceptJS v1.4.2
Using test root "/path/to/codeceptjs-sample"
Helpers: Puppeteer, Sample
Plugins: screenshotOnFail
sample --
[1] Starting recording promises
Emitted | suite.before ([object Object])
sample
Emitted | test.before ([object Object])
Emitted | test.start ([object Object])
Emitted | step.before (I am on page "/")
Emitted | step.after (I am on page "/")
Emitted | step.before (I click "a")
Emitted | step.after (I click "a")
Emitted | step.before (I wait for element "#toIndex2")
Emitted | step.after (I wait for element "#toIndex2")
Emitted | step.start (I am on page "/")
I am on page "/"
› [Url] http://localhost/
› [Browser:Error] Failed to load resource: the server responded with a status of 404 (Not Found)
Emitted | step.passed (I am on page "/")
Emitted | step.finish (I am on page "/")
Emitted | step.start (I click "a")
I click "a"
› [Url] http://localhost/index2.html
Emitted | step.passed (I click "a")
Emitted | step.finish (I click "a")
Emitted | step.start (I wait for element "#toIndex2")
I wait for element "#toIndex2"
› [Url] http://localhost/index.html
(node:80695) UnhandledPromiseRejectionWarning: Error: Execution context was destroyed, most likely because of a navigation.
at rewriteError (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/ExecutionContext.js:144:15)
at process._tickCallback (internal/process/next_tick.js:68:7)
(node:80695) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
(node:80695) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
Emitted | step.passed (I wait for element "#toIndex2")
Emitted | step.finish (I wait for element "#toIndex2")
Emitted | test.passed ([object Object])
Emitted | test.finish ([object Object])
✔ OK in 1169ms
Emitted | test.after ([object Object])
Emitted | suite.after ([object Object])
OK | 1 passed // 3s
Emitted | global.result ([object Object])
Emitted | global.after ([object Object])
$
Provide test source code if related
index.html
<a id="toIndex2" href="index2.html">index2</a>
index2.html
<html>
<head>
<meta http-equiv="refresh" content="0;URL='http://localhost/index.html'" />
</head>
<body>
<a href="index.html">index</a>
</body>
</html>
test code on CodeceptJS
Feature('sample');
Scenario('sample', (I) => {
I.amOnPage('/');
I.click('a');
I.waitForElement('#toIndex2');
});
Details
- CodeceptJS version: 1.4.2
- NodeJS Version: v10.10.0
- Operating System: macOS High Sierra
- Protractor || WebDriverIO || Nightmare version (if related)
- Configuration file:
{
"output": "./output",
"helpers": {
"Puppeteer": {
"url": "http://localhost",
"windowSize": "1280x800",
"waitForNavigation": "networkidle0",
"waitForTimeout": 10000,
"chrome": {
"args": [
"--lang=ja,en-US,en"
],
"ignoreHTTPSErrors": true
},
"show": true
},
"Sample": {
"require": "./sample_helper.js"
}
},
"include": {
"I": "./steps_file.js"
},
"mocha": {},
"bootstrap": false,
"teardown": null,
"hooks": [],
"gherkin": {},
"plugins": {
"screenshotOnFail": {
"enabled": true
}
},
"tests": "./*_test.js",
"timeout": 10000,
"name": "sample"
}
I have the same Problem when the refresh is triggered by javascript
Try calling I.waitForNavigation(), after I.click('a').
@brendonbarreto
Thanks for your suggestion.
I've tried I.waitForNavigation() after I.click('a')
But it doesn't solve the issue..
Test Code
Scenario('sample', (I) => {
I.amOnPage('/');
I.click('a');
I.waitForNavigation();
I.waitForElement('#toIndex2');
});
Console Log
$ ./node_modules/.bin/codeceptjs run --steps --verbose
CodeceptJS v1.4.2
Using test root "/path/to/codeceptjs-sample"
Helpers: Puppeteer
Plugins: screenshotOnFail
sample --
[1] Starting recording promises
Emitted | suite.before ([object Object])
sample
Emitted | test.before ([object Object])
Emitted | test.start ([object Object])
Emitted | step.before (I am on page "/")
Emitted | step.after (I am on page "/")
Emitted | step.before (I click "a")
Emitted | step.after (I click "a")
Emitted | step.before (I wait for navigation )
Emitted | step.after (I wait for navigation )
Emitted | step.before (I wait for element "#toIndex2")
Emitted | step.after (I wait for element "#toIndex2")
Emitted | step.start (I am on page "/")
I am on page "/"
› [Url] http://localhost/
Emitted | step.passed (I am on page "/")
Emitted | step.finish (I am on page "/")
Emitted | step.start (I click "a")
I click "a"
› [Url] http://localhost/index2.html
› [Url] http://localhost/index.html
(node:16901) UnhandledPromiseRejectionWarning: Error: Execution context was destroyed, most likely because of a navigation.
at rewriteError (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/ExecutionContext.js:144:15)
at process._tickCallback (internal/process/next_tick.js:68:7)
-- ASYNC --
at ExecutionContext.<anonymous> (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/helper.js:144:27)
at ElementHandle.$ (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/ExecutionContext.js:512:50)
at ElementHandle.<anonymous> (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/helper.js:145:23)
at Frame.$ (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/FrameManager.js:448:34)
at process._tickCallback (internal/process/next_tick.js:68:7)
-- ASYNC --
at Frame.<anonymous> (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/helper.js:144:27)
at Page.$ (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/Page.js:276:29)
at Page.<anonymous> (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/helper.js:145:23)
at Page.page.on.frame (/path/to/codeceptjs-sample/node_modules/codeceptjs/lib/helper/Puppeteer.js:2049:48)
at Page.emit (events.js:182:13)
at CDPSession.Page.client.on.event (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/Page.js:131:52)
at CDPSession.emit (events.js:182:13)
at CDPSession._onMessage (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/Connection.js:216:12)
at Connection._onMessage (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/Connection.js:99:19)
at WebSocketTransport._ws.addEventListener.event (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/WebSocketTransport.js:41:24)
-- ASYNC --
at Page.<anonymous> (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/helper.js:144:27)
at Page.page.on.frame (/path/to/codeceptjs-sample/node_modules/codeceptjs/lib/helper/Puppeteer.js:2049:48)
at Page.emit (events.js:182:13)
at CDPSession.Page.client.on.event (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/Page.js:131:52)
at CDPSession.emit (events.js:182:13)
at CDPSession._onMessage (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/Connection.js:216:12)
at Connection._onMessage (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/Connection.js:99:19)
at WebSocketTransport._ws.addEventListener.event (/path/to/codeceptjs-sample/node_modules/puppeteer/lib/WebSocketTransport.js:41:24)
at WebSocket.onMessage (/path/to/codeceptjs-sample/node_modules/ws/lib/event-target.js:120:16)
at WebSocket.emit (events.js:182:13)
(node:16901) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
(node:16901) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
Emitted | step.passed (I click "a")
Emitted | step.finish (I click "a")
Emitted | step.start (I wait for navigation )
I wait for navigation
$
I've tried 1.4.4. But it didn't solve this issue.
Tried on CodeceptJS 2.0.1, and with waitForNavigation solution but didn't work. Any suggestion will be appreciated.
I'm also having this issue, did anyone find a solution?
I too am having this issue. Would very much appreciate any insight on this.
EDIT - Updating to 2.1.4 appears to have solved the problem. Thank you.
I have this issue too codeceptjs 2.5.0
I also have this issue with codeceptjs 6.14.11
Login and Logout -- I am on page "/" (node:45775) UnhandledPromiseRejectionWarning: page.evaluate: Execution context was destroyed, most likely because of a navigation. Error: at Object.captureStackTrace
It works for me using
I.waitForNavigation() after I.click()
Tried on
"puppeteer": "1.6.0"
"codeceptjs": "^2.3.5",
Ran into the same issue with I.amOnPage('/loginwithredirect') intermittently (maybe once in every 3 or 5 runs). Did not work for me even after I added I.waitForNavigation() after that.
Tried on: "codeceptjs": "3.2.1" "playwright": "^1",
Also tried on "puppeteer": "11.0.0"
I got around it by wrapping the I.amOnPage with tryTo(), which continues my test alright despite the error.
be sure that you put I.waitForNavigation() in correct line.
Hi there, yes this issue is annoying. I think pupeteer is not maintained any more. I tried to refacor the puppeteer helper (PR #2672) but failed.
My npm postInstall replaces the puppeteer.js with some fixes. May be I will find some time to create a PR in the future.
I use promise-retry for the problematic steps
const promiseRetry = require('promise-retry');
async waitForNavigation(opts = {}) {
opts = {
timeout: this.options.getPageTimeout,
waitUntil: this.options.waitForNavigation,
...opts
};
return promiseRetry(
(retry, number) => {
this.debug(`waitForNavigation: Attempt #${number}`);
return this.page.waitForNavigation(opts).catch(error => {
if (error && typeof error.message === 'string' && error.message.indexOf('context') > -1) {
return retry(error);
}
throw error;
});
},
{ retries: 9, minTimeout: 10, factor: 1 }
);
}
async function targetCreatedHandler(page) {
if (!page) return;
this.withinLocator = null;
page.on('domcontentloaded', () => {
this.context = promiseRetry(
(retry, number) => {
this.debug(`on domcontentloaded: Attempt #${number}`);
return page.$('body').catch(retry);
},
{ retries: 9, minTimeout: 10, factor: 1 }
).catch(err => {
this.debug(`on domcontentloaded: error getting body:\n${err.toString()}`);
return page;
});
});
page.on('console', msg => {
this.debugSection(`Browser:${ucfirst(msg.type())}`, (msg._text || '') + msg.args().join(' '));
consoleLogStore.add(msg);
});
I also changed the recorder.retry({ that is set in _before() because it's too generic and also does not work always.
May be this helps you.
Please reopen if you encounter this with latest version.