diff --git a/packages/flex-plugin-e2e-tests/src/tests/step006.ts b/packages/flex-plugin-e2e-tests/src/tests/step006.ts index 0e5ba7856..fa4204f39 100644 --- a/packages/flex-plugin-e2e-tests/src/tests/step006.ts +++ b/packages/flex-plugin-e2e-tests/src/tests/step006.ts @@ -1,5 +1,6 @@ /* eslint-disable */ import { replaceInFile } from 'replace-in-file'; +import { logger } from '@twilio/flex-dev-utils'; import { TestSuite, TestParams, testParams } from '../core'; import { spawn, Browser, pluginHelper, joinPath, assertion, killChildProcess, retryOnError } from '../utils'; @@ -21,16 +22,25 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: testParams.config.start.timeout, testParams.config.start.pollInterval, ); - await Browser.create({ flex: plugin.localhostUrl, twilioConsole: config.consoleBaseUrl }); const loginAndAssert = async (firstLoad: boolean) => { + // Recreate browser on each attempt to avoid using detached pages + if (!firstLoad) { + await Browser.kill(); + } + await Browser.create({ flex: plugin.localhostUrl, twilioConsole: config.consoleBaseUrl }); + await Browser.app.twilioConsole.login('agent-desktop', secrets.api.accountSid, config.localhostPort, firstLoad); await assertion.app.view.agentDesktop.isVisible(); await assertion.app.view.plugins.plugin.isVisible(plugin.componentText); }; - const onError = async (e: any) => { - await Browser.app.takeScreenshot(environment.cwd, 'step006_failure.png'); + const onError = async () => { + try { + await Browser.app.takeScreenshot(environment.cwd, 'step006_failure.png'); + } catch (screenshotError) { + logger.error('Failed to take screenshot:', screenshotError); + } }; const onFinally = async () => { diff --git a/packages/flex-plugin-e2e-tests/src/tests/step010.ts b/packages/flex-plugin-e2e-tests/src/tests/step010.ts index 5d1ceade8..e9391f5da 100644 --- a/packages/flex-plugin-e2e-tests/src/tests/step010.ts +++ b/packages/flex-plugin-e2e-tests/src/tests/step010.ts @@ -29,22 +29,25 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: throw new Error(`Did not find plugin with name: ${plugin.name} in released plugins`); } - await Browser.create({ flex: config.hostedFlexBaseUrl, twilioConsole: config.consoleBaseUrl }); - // Log into Flex - await Browser.app.twilioConsole.login('admin', secrets.api.accountSid, config.localhostPort); + const loginAndAssert = async (firstLoad: boolean) => { + // Recreate browser on each attempt to avoid using detached pages + if (!firstLoad) { + await Browser.kill(); + } + await Browser.create({ flex: config.hostedFlexBaseUrl, twilioConsole: config.consoleBaseUrl }); - await assertion.app.view.adminDashboard.isVisible(); + // Log into Flex + await Browser.app.twilioConsole.login('admin', secrets.api.accountSid, config.localhostPort); - // Verify that user is on the right account - const accountSid = await Browser.app.getFlexAccountSid(); - assertion.equal(accountSid, secrets.api.accountSid); - // Make sure that /plugins contain the plugin - await pluginHelper.waitForPluginToRelease(releasedPlugin, PLUGIN_RELEASED_TIMEOUT, PLUGIN_RELEASED_POLL_INTERVAL); - // await assertRetry(); + await assertion.app.view.adminDashboard.isVisible(); - const loginAndAssert = async () => { - // Load local plugin + // Verify that user is on the right account + const accountSid = await Browser.app.getFlexAccountSid(); + assertion.equal(accountSid, secrets.api.accountSid); + // Make sure that /plugins contain the plugin + await pluginHelper.waitForPluginToRelease(releasedPlugin, PLUGIN_RELEASED_TIMEOUT, PLUGIN_RELEASED_POLL_INTERVAL); + // Load local plugin await Browser.app.agentDesktop.open(); logger.info('Agent Desktop opened'); @@ -52,8 +55,12 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: await assertion.app.view.plugins.plugin.isVisible(plugin.newlineValue!); }; - const onError = async (e: any) => { - await Browser.app.takeScreenshot(environment.cwd, 'step010_failure.png'); + const onError = async () => { + try { + await Browser.app.takeScreenshot(environment.cwd, 'step010_failure.png'); + } catch (screenshotError) { + logger.error('Failed to take screenshot:', screenshotError); + } }; const onFinally = async () => { diff --git a/packages/flex-plugin-e2e-tests/src/tests/step011.ts b/packages/flex-plugin-e2e-tests/src/tests/step011.ts index 52de4652d..db48082f3 100644 --- a/packages/flex-plugin-e2e-tests/src/tests/step011.ts +++ b/packages/flex-plugin-e2e-tests/src/tests/step011.ts @@ -1,4 +1,6 @@ /* eslint-disable import/no-unused-modules */ +import { logger } from '@twilio/flex-dev-utils'; + import { TestSuite, TestParams, testParams } from '../core'; import { spawn, Browser, pluginHelper, assertion, killChildProcess, retryOnError } from '../utils'; @@ -26,10 +28,13 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: { detached: true, cwd: plugin3.dir }, ); await Promise.all([startPlugin(plugin2.localhostUrl), startPlugin(plugin3.localhostUrl)]); - await Browser.create({ flex: plugin3.localhostUrl, twilioConsole: config.consoleBaseUrl }); const loginAndAssert = async (firstLoad: boolean) => { - // Load local plugin + // Recreate browser on each attempt to avoid using detached pages + if (!firstLoad) { + await Browser.kill(); + } + await Browser.create({ flex: plugin3.localhostUrl, twilioConsole: config.consoleBaseUrl }); await Browser.app.twilioConsole.login('agent-desktop', secrets.api.accountSid, config.localhostPort, firstLoad); @@ -42,8 +47,12 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: await assertion.app.view.plugins.plugin.isVisible(plugin3.componentText); }; - const onError = async (e: any) => { - await Browser.app.takeScreenshot(environment.cwd, 'step011_failure.png'); + const onError = async () => { + try { + await Browser.app.takeScreenshot(environment.cwd, 'step011_failure.png'); + } catch (screenshotError) { + logger.error('Failed to take screenshot:', screenshotError); + } }; const onFinally = async () => { diff --git a/packages/flex-plugin-e2e-tests/src/tests/step012.ts b/packages/flex-plugin-e2e-tests/src/tests/step012.ts index 4b8c16088..096bd1bec 100644 --- a/packages/flex-plugin-e2e-tests/src/tests/step012.ts +++ b/packages/flex-plugin-e2e-tests/src/tests/step012.ts @@ -1,5 +1,6 @@ /* eslint-disable import/no-unused-modules */ import semver from 'semver'; +import { logger } from '@twilio/flex-dev-utils'; import { TestSuite, TestParams, testParams } from '../core'; import { spawn, Browser, pluginHelper, api, assertion, killChildProcess, retryOnError } from '../utils'; @@ -51,9 +52,13 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: testParams.config.start.pollInterval, ); - await Browser.create({ flex: plugin3.localhostUrl, twilioConsole: config.consoleBaseUrl }); - const loginAndAssert = async (firstLoad: boolean) => { + // Recreate browser on each attempt to avoid using detached pages + if (!firstLoad) { + await Browser.kill(); + } + await Browser.create({ flex: plugin3.localhostUrl, twilioConsole: config.consoleBaseUrl }); + await Browser.app.twilioConsole.login('agent-desktop', secrets.api.accountSid, config.localhostPort, firstLoad); // Check if local plugin loaded okay @@ -65,8 +70,12 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: await assertion.app.view.plugins.plugin.isVisible(plugin3.componentText); }; - const onError = async (e: any) => { - await Browser.app.takeScreenshot(environment.cwd, 'step012_failure.png'); + const onError = async () => { + try { + await Browser.app.takeScreenshot(environment.cwd, 'step012_failure.png'); + } catch (screenshotError) { + logger.error('Failed to take screenshot:', screenshotError); + } }; const onFinally = async () => { diff --git a/packages/flex-plugin-e2e-tests/src/tests/step013.ts b/packages/flex-plugin-e2e-tests/src/tests/step013.ts index 027248dde..30fd6ec2f 100644 --- a/packages/flex-plugin-e2e-tests/src/tests/step013.ts +++ b/packages/flex-plugin-e2e-tests/src/tests/step013.ts @@ -1,6 +1,7 @@ /* eslint-disable import/no-unused-modules */ import { replaceInFile } from 'replace-in-file'; import semver from 'semver'; +import { logger } from '@twilio/flex-dev-utils'; import { TestSuite, TestParams, testParams } from '../core'; import { spawn, Browser, pluginHelper, joinPath, assertion, killChildProcess, api, retryOnError } from '../utils'; @@ -54,10 +55,14 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: cwd: plugin3.dir, }); await Promise.all([startPlugin(plugin2.localhostUrl), startPlugin(plugin3.localhostUrl)]); - await Browser.create({ flex: plugin3.localhostUrl, twilioConsole: config.consoleBaseUrl }); const loginAndAssert = async (firstLoad: boolean) => { - // Load local plugin + // Recreate browser on each attempt to avoid using detached pages + if (!firstLoad) { + await Browser.kill(); + } + await Browser.create({ flex: plugin3.localhostUrl, twilioConsole: config.consoleBaseUrl }); + await Browser.app.twilioConsole.login('agent-desktop', secrets.api.accountSid, config.localhostPort, firstLoad); // Check if local plugin loaded okay @@ -69,8 +74,12 @@ const testSuite: TestSuite = async ({ scenario, config, secrets, environment }: await assertion.app.view.plugins.plugin.isVisible(plugin3.componentText); }; - const onError = async (e: any) => { - await Browser.app.takeScreenshot(environment.cwd, 'step013_failure.png'); + const onError = async () => { + try { + await Browser.app.takeScreenshot(environment.cwd, 'step013_failure.png'); + } catch (screenshotError) { + logger.error('Failed to take screenshot:', screenshotError); + } }; const onFinally = async () => { diff --git a/packages/flex-plugin-e2e-tests/src/utils/pages/view/base.ts b/packages/flex-plugin-e2e-tests/src/utils/pages/view/base.ts index cf6f9343b..664acb3a6 100644 --- a/packages/flex-plugin-e2e-tests/src/utils/pages/view/base.ts +++ b/packages/flex-plugin-e2e-tests/src/utils/pages/view/base.ts @@ -30,18 +30,12 @@ export abstract class Base { }): Promise { const fullPath = path ? `${baseUrl}/${path}` : baseUrl; try { - await Promise.all([ - this.page.waitForNavigation({ - waitUntil: 'networkidle2', // condition to consider navigation finished - timeout: Base.DEFAULT_PAGE_LOAD_TIMEOUT, - }), - this.page.goto(fullPath, { - waitUntil: waitUntil || 'networkidle2', - timeout: Base.DEFAULT_PAGE_LOAD_TIMEOUT, - }), - ]); + await this.page.goto(fullPath, { + waitUntil: waitUntil || 'networkidle2', + timeout: Base.DEFAULT_PAGE_LOAD_TIMEOUT, + }); } catch (err) { - if (err.message.includes('detached')) { + if (err instanceof Error && err.message.includes('detached')) { logger.error('Page has been detached. adding a sleep to let other processes finish'); /* * Just let it wait the rest of the timeout so the other contestants in the rest @@ -49,7 +43,8 @@ export abstract class Base { */ await sleep(5000); } - // Intentionally doing nothing on error + // Re-throw all errors so they propagate to test error handlers for screenshots + throw err; } }