diff --git a/.github/workflows/test-milo.yml b/.github/workflows/test-milo.yml index a08007b5..2a5ce21a 100644 --- a/.github/workflows/test-milo.yml +++ b/.github/workflows/test-milo.yml @@ -25,3 +25,32 @@ jobs: curl -X POST 'https://dc.ci.corp.adobe.com/job/DC%20Release%20-%20Run%20Nala/buildWithParameters?token=${{ secrets.JNK_JOB_TOKEN }}&branch=main' \ -u '${{ secrets.JNK_USER }}:${{ secrets.JNK_API_TOKEN }}' + run-tests-gha: + name: Smoke Test + runs-on: ubuntu-latest + steps: + - name: Check out repository + uses: actions/checkout@v3 + + - name: Cache dependencies + id: cache + uses: actions/cache@v3 + with: + path: ./node_modules + key: modules-${{ hashFiles('package-lock.json') }} + + - name: Install dependencies + if: steps.cache.outputs.cache-hit != 'true' + run: npm ci --ignore-scripts + + - name: Install Playwright + run: npx playwright install --with-deps chromium + + - name: Run the tests + run: xvfb-run -a npx run test/e2e/frictionless -t @smoke-converter + + - name: Save test logs + uses: actions/upload-artifact@v3 + with: + name: reports + path: reports/ \ No newline at end of file diff --git a/acrobat/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.js b/acrobat/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.js index 8d987583..26af720d 100644 --- a/acrobat/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.js +++ b/acrobat/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.js @@ -23,6 +23,7 @@ const localeMap = { 'gr_el': 'el-gr', 'ie': 'en-ie', 'il_en': 'en-il', + 'il_he': 'he-il', 'it': 'it-it', 'lv': 'lv-lv', 'lt': 'lt-lt', diff --git a/acrobat/blocks/dc-converter-widget/dc-converter-widget.js b/acrobat/blocks/dc-converter-widget/dc-converter-widget.js index b192f368..99acc7ed 100644 --- a/acrobat/blocks/dc-converter-widget/dc-converter-widget.js +++ b/acrobat/blocks/dc-converter-widget/dc-converter-widget.js @@ -16,16 +16,17 @@ const localeMap = { 'cy_en': 'en-cy', 'dk': 'da-dk', 'de': 'de-de', - 'ee': 'en-ee', + 'ee': 'et-ee', 'es': 'es-es', 'fr': 'fr-fr', 'gr_en': 'en-gr', 'gr_el': 'el-gr', 'ie': 'en-ie', 'il_en': 'en-il', + 'il_he': 'he-il', 'it': 'it-it', - 'lv': 'en-lv', - 'lt': 'en-lt', + 'lv': 'lv-lv', + 'lt': 'lt-lt', 'lu_de': 'de-lu', 'lu_en': 'en-lu', 'lu_fr': 'fr-lu', @@ -40,7 +41,7 @@ const localeMap = { 'pt': 'pt-pt', 'ro': 'ro-ro', 'ch_de': 'de-ch', - 'si': 'si-si', + 'si': 'sl-si', 'sk': 'sk-sk', 'ch_fr': 'fr-ch', 'fi': 'fi-fi', @@ -48,9 +49,9 @@ const localeMap = { 'ch_it': 'it-ch', 'tr': 'tr-tr', 'uk': 'en-uk', - 'bg': 'en-bg', + 'bg': 'bg-bg', 'ru': 'ru-ru', - 'ua': 'ua-ua', + 'ua': 'uk-ua', 'au': 'en-au', 'hk_en': 'en-hk', 'in': 'en-in', @@ -117,7 +118,7 @@ let url = new URL(window.location.href); let langFromPath = url.pathname.split('/')[1]; const pageLang = localeMap[langFromPath] || 'en-us'; -export default function init(element) { +export default async function init(element) { redirectLegacyBrowsers(); element.closest('main > div').dataset.section = 'widget'; const widget = element; @@ -148,7 +149,7 @@ export default function init(element) { if (window.location.hostname === 'www.adobe.com') { WIDGET_ENV = `https://acrobat.adobe.com/dc-hosted/${DC_WIDGET_VERSION}/dc-app-launcher.js`; - DC_DOMAIN = 'https://acrobat.adobe.com'; + DC_DOMAIN = 'https://www.adobe.com/dc'; ENV = 'prod'; } @@ -158,7 +159,7 @@ export default function init(element) { || window.location.hostname === 'main--dc--adobecom.hlx.live' || window.location.hostname === 'www.stage.adobe.com') { WIDGET_ENV = `https://stage.acrobat.adobe.com/dc-hosted/${STG_DC_WIDGET_VERSION}/dc-app-launcher.js`; - DC_DOMAIN = 'https://stage.acrobat.adobe.com'; + DC_DOMAIN = 'https://www.stage.adobe.com/dc'; DC_GENERATE_CACHE_VERSION = STG_DC_GENERATE_CACHE_VERSION; ENV = 'stage'; } @@ -202,26 +203,23 @@ export default function init(element) { const isReturningUser = window.localStorage.getItem('pdfnow.auth'); const isRedirection = /redirect_(?:conversion|files)=true/.test(window.location.search); const preRenderDropZone = !isReturningUser && !isRedirection; - if (preRenderDropZone) { - (async () => { - // TODO: Make dynamic - const response = await fetch(DC_GENERATE_CACHE_URL || `${DC_DOMAIN}/dc-generate-cache/dc-hosted-${DC_GENERATE_CACHE_VERSION}/${VERB}-${pageLang}.html`); - switch (response.status) { - case 200: { - const template = await response.text(); - if (!("rendered" in widgetContainer.dataset)) { - widgetContainer.dataset.rendered = "true"; - const doc = new DOMParser().parseFromString(template, 'text/html'); - document.head.appendChild(doc.head.getElementsByTagName('Style')[0]); - widgetContainer.appendChild(doc.body.firstElementChild); - performance.mark("milo-insert-snippet"); - } - break; + if (VERB === 'compress-pdf' || preRenderDropZone) { + const response = await fetch(DC_GENERATE_CACHE_URL || `${DC_DOMAIN}/dc-generate-cache/dc-hosted-${DC_GENERATE_CACHE_VERSION}/${VERB}-${pageLang}.html`); + switch (response.status) { + case 200: { + const template = await response.text(); + if (!("rendered" in widgetContainer.dataset)) { + widgetContainer.dataset.rendered = "true"; + const doc = new DOMParser().parseFromString(template, 'text/html'); + document.head.appendChild(doc.head.getElementsByTagName('Style')[0]); + widgetContainer.appendChild(doc.body.firstElementChild); + performance.mark("milo-insert-snippet"); } - default: - break; + break; } - })(); + default: + break; + } } window.addEventListener('IMS:Ready', async () => { diff --git a/acrobat/blocks/list.js b/acrobat/blocks/list.js index 683d3967..40f8e640 100644 --- a/acrobat/blocks/list.js +++ b/acrobat/blocks/list.js @@ -3,7 +3,6 @@ const blocks = [ 'eventwrapper', 'personalization', 'verb-subfooters', - 'promotion' ]; export default blocks; diff --git a/acrobat/blocks/promotion/promotion.css b/acrobat/blocks/promotion/promotion.css deleted file mode 100644 index e69de29b..00000000 diff --git a/acrobat/blocks/promotion/promotion.js b/acrobat/blocks/promotion/promotion.js deleted file mode 100644 index d9f6a2f3..00000000 --- a/acrobat/blocks/promotion/promotion.js +++ /dev/null @@ -1,26 +0,0 @@ -export default async function init(el) { - const locale = 'en-US'; - const promotionName = el.getAttribute('data-promotion'); - const response = await window.fetch(`${locale === 'en-US' ? '' : `/${locale}`}/dc-shared/fragments/short-form-pages/promotions/${promotionName}.plain.html`); - if (!response.ok) { - // No valid response - return; - } - const promotionContent = await response.text(); - if (!promotionContent.length) { - // No content in document - return; - } - - el.appendChild(document.createRange() - .createContextualFragment(promotionContent)); -} - -// Solution for FedPub promotions -export const promotionFromMetadata = async (metadata) => { - const promo = document.createElement('div'); - promo.classList.add('promotion'); - promo.setAttribute('data-promotion', metadata.toLowerCase()); - document.querySelector('main > div').appendChild(promo); - init(promo); -}; diff --git a/acrobat/scripts/contentSecurityPolicy/prod.js b/acrobat/scripts/contentSecurityPolicy/prod.js index c0d5b364..1de68588 100644 --- a/acrobat/scripts/contentSecurityPolicy/prod.js +++ b/acrobat/scripts/contentSecurityPolicy/prod.js @@ -143,6 +143,8 @@ const imgSrc = [ 'milo.adobe.com', 'p.typekit.net', 's.tgm.yahoo-net.jp', + 's.yimg.jp', + 'yjtag.yahoo.co.jp', ';', ]; @@ -222,6 +224,9 @@ const scriptSrc = [ 'tag.demandbase.com', '*.typekit.net', 'zn3n5vyia1vy8b4ly-adobe.siteintercept.qualtrics.com/', + 's.yjtag.jp/tag.js', + 's.yimg.jp', + 'yjtag.yahoo.co.jp', ';', ]; diff --git a/acrobat/scripts/contentSecurityPolicy/stage.js b/acrobat/scripts/contentSecurityPolicy/stage.js index db6dbc1f..f6ce24ae 100644 --- a/acrobat/scripts/contentSecurityPolicy/stage.js +++ b/acrobat/scripts/contentSecurityPolicy/stage.js @@ -150,6 +150,8 @@ const imgSrc = [ 'http://localhost:6456/', '*.hlx.page', '*.hlx.live', + 's.yimg.jp', + 'yjtag.yahoo.co.jp', ';', ]; @@ -238,6 +240,9 @@ const scriptSrc = [ 'http://localhost:6456/', '*.hlx.page', '*.hlx.live', + 's.tgm.yahoo-net.jp', + 's.yimg.jp', + 'yjtag.yahoo.co.jp', ';', ]; diff --git a/acrobat/scripts/maps/localeMap.js b/acrobat/scripts/maps/localeMap.js index c5dad126..67512d16 100644 --- a/acrobat/scripts/maps/localeMap.js +++ b/acrobat/scripts/maps/localeMap.js @@ -40,6 +40,12 @@ const localeMap = { 'br': 'pt-BR', 'la': 'es-ES', 'mx': 'es-ES', - 'be_nl': 'nl-NL' + 'be_nl': 'nl-NL', + 'bg': 'bg-BG', + 'ee': 'et-EE', + 'lt': 'lt-LT', + 'lv': 'lv-LV', + 'ua': 'uk-UA', + 'si': 'sl-SI' }; export default localeMap; diff --git a/acrobat/scripts/scripts.js b/acrobat/scripts/scripts.js index c003eccf..95bebad4 100644 --- a/acrobat/scripts/scripts.js +++ b/acrobat/scripts/scripts.js @@ -89,7 +89,7 @@ const locales = { cy_en: { ietf: 'en-CY', tk: 'pps7abe.css' }, dk: { ietf: 'da-DK', tk: 'aaz7dvd.css' }, de: { ietf: 'de-DE', tk: 'vin7zsi.css' }, - ee: { ietf: 'en-EE', tk: 'aaz7dvd.css' }, + ee: { ietf: 'et-EE', tk: 'aaz7dvd.css' }, es: { ietf: 'es-ES', tk: 'oln4yqj.css' }, fr: { ietf: 'fr-FR', tk: 'vrk5vyv.css' }, gr_en: { ietf: 'en-GR', tk: 'pps7abe.css' }, @@ -111,7 +111,7 @@ const locales = { ro: { ietf: 'en-RO', tk: 'aaz7dvd.css' }, sa_en: { ietf: 'en', tk: 'pps7abe.css' }, ch_de: { ietf: 'de-CH', tk: 'vin7zsi.css' }, - si: { ietf: 'en-SI', tk: 'aaz7dvd.css' }, + si: { ietf: 'sl-SI', tk: 'aaz7dvd.css' }, sk: { ietf: 'en-SK', tk: 'aaz7dvd.css' }, ch_fr: { ietf: 'fr-CH', tk: 'vrk5vyv.css' }, fi: { ietf: 'fi-FI', tk: 'aaz7dvd.css' }, @@ -122,9 +122,9 @@ const locales = { uk: { ietf: 'en-GB', tk: 'pps7abe.css' }, at: { ietf: 'de-AT', tk: 'vin7zsi.css' }, cz: { ietf: 'cs-CZ', tk: 'aaz7dvd.css' }, - bg: { ietf: 'en-BG', tk: 'aaz7dvd.css' }, + bg: { ietf: 'bg-BG', tk: 'aaz7dvd.css' }, ru: { ietf: 'ru-RU', tk: 'aaz7dvd.css' }, - ua: { ietf: 'en-UA', tk: 'aaz7dvd.css' }, + ua: { ietf: 'uk-UA', tk: 'aaz7dvd.css' }, il_he: { ietf: 'he', tk: 'nwq1mna.css', dir: 'rtl' }, ae_ar: { ietf: 'ar', tk: 'nwq1mna.css', dir: 'rtl' }, mena_ar: { ietf: 'ar', tk: 'dis2dpj.css', dir: 'rtl' }, @@ -203,32 +203,31 @@ const { ietf } = getLocale(locales); (async function loadPage() { // Fast track the widget - (async () => { - const widgetBlock = document.querySelector('[class*="dc-converter-widget"]'); - if (widgetBlock) { - const blockName = widgetBlock.classList.value; - widgetBlock.removeAttribute('class'); - widgetBlock.id = 'dc-converter-widget'; - const DC_WIDGET_VERSION = document.querySelector('meta[name="dc-widget-version"]')?.getAttribute('content'); - const [,DC_GENERATE_CACHE_VERSION] = DC_WIDGET_VERSION.split('_'); - const dcUrls = [ - `https://acrobat.adobe.com/dc-hosted/${DC_WIDGET_VERSION}/dc-app-launcher.js`, - `https://acrobat.adobe.com/dc-generate-cache/dc-hosted-${DC_GENERATE_CACHE_VERSION}/${window.location.pathname.split('/').pop().split('.')[0]}-${ietf.toLowerCase()}.html` - ]; + const widgetBlock = document.querySelector('[class*="dc-converter-widget"]'); + if (widgetBlock) { + const blockName = widgetBlock.classList.value; + widgetBlock.removeAttribute('class'); + widgetBlock.id = 'dc-converter-widget'; + const DC_WIDGET_VERSION = document.querySelector('meta[name="dc-widget-version"]')?.getAttribute('content'); + const DC_GENERATE_CACHE_VERSION = document.querySelector('meta[name="dc-generate-cache-version"]')?.getAttribute('content'); + const dcUrls = [ + `https://www.adobe.com/dc/dc-generate-cache/dc-hosted-${DC_GENERATE_CACHE_VERSION}/${window.location.pathname.split('/').pop().split('.')[0]}-${ietf.toLowerCase()}.html`, + `https://acrobat.adobe.com/dc-hosted/${DC_WIDGET_VERSION}/dc-app-launcher.js` + ]; - dcUrls.forEach( url => { - const link = document.createElement('link'); - link.setAttribute('rel', 'prefetch'); - if(url.split('.').pop() === 'html') {link.setAttribute('as', 'fetch');} - if(url.split('.').pop() === 'js') {link.setAttribute('as', 'script');;} - link.setAttribute('href', url); - document.head.appendChild(link); - }) + dcUrls.forEach( url => { + const link = document.createElement('link'); + link.setAttribute('rel', 'prefetch'); + if(url.split('.').pop() === 'html') {link.setAttribute('as', 'fetch');} + if(url.split('.').pop() === 'js') {link.setAttribute('as', 'script');;} + link.setAttribute('href', url); + link.setAttribute('crossorigin', ''); + document.head.appendChild(link); + }) - const { default: dcConverter } = await import(`../blocks/${blockName}/${blockName}.js`); - dcConverter(widgetBlock); - } - })(); + const { default: dcConverter } = await import(`../blocks/${blockName}/${blockName}.js`); + await dcConverter(widgetBlock); + } // Setup CSP (async () => { @@ -253,16 +252,9 @@ const { ietf } = getLocale(locales); addLocale(ietf); setConfig({ ...CONFIG, miloLibs }); loadLana({ clientId: 'dxdc' }); - // get event back form dc web and then load area + // get event back form dc web and then load area await loadArea(document, false); - // Promotion from metadata (for FedPub) - const promotionMetadata = getMetadata('promotion'); - if (promotionMetadata && !document.querySelector('main .promotion')) { - const { promotionFromMetadata } = await import('../blocks/promotion/promotion.js'); - promotionFromMetadata(promotionMetadata); - } - // Setup Logging const { default: lanaLogging } = await import('./dcLana.js'); lanaLogging(); diff --git a/acrobat/styles/styles.css b/acrobat/styles/styles.css index ee25de03..a88e6ff3 100644 --- a/acrobat/styles/styles.css +++ b/acrobat/styles/styles.css @@ -234,7 +234,7 @@ div.how-to { /* Full Screen Widget */ @media (max-width: 600px) { .fsw > div > div { - height: calc(100vh - 100px); + min-height: calc(100vh - 100px) !important; } } diff --git a/head.html b/head.html index e3011f1f..19c16bf1 100644 --- a/head.html +++ b/head.html @@ -1,5 +1,5 @@ - + diff --git a/package-lock.json b/package-lock.json index cfa1faa3..6e64b8ef 100644 --- a/package-lock.json +++ b/package-lock.json @@ -12,8 +12,11 @@ "bowser": "^2.11.0" }, "devDependencies": { + "@amwp/platform-ui-automation": "^0.0.2", + "@amwp/platform-ui-lib-adobe": "^0.0.2", "@babel/core": "7.17.7", "@babel/eslint-parser": "7.17.0", + "@babel/register": "7.17.0", "@esm-bundle/chai": "4.3.4-fix.0", "@web/dev-server-import-maps": "^0.0.6", "@web/test-runner": "0.13.27", @@ -44,6 +47,78 @@ "node": ">=6.0.0" } }, + "node_modules/@amwp/platform-ui-automation": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/@amwp/platform-ui-automation/-/platform-ui-automation-0.0.2.tgz", + "integrity": "sha512-/VZFjTIsicmmYjr6CpwfptS9u5Yd5PeflkirZO8CngTYh7HHcmwjg/WPULKA1tSDseKXuQxsxjKYNeZx1gMCIA==", + "dev": true, + "dependencies": { + "@cucumber/cucumber": "^8.9.1", + "@cucumber/pretty-formatter": "^1.0.0", + "@playwright/test": "^1.31.2", + "is-ci": "^3.0.1", + "js-yaml": "^4.1.0", + "node-fetch": "^2.6.9", + "node-html-parser": "^6.1.4", + "playwright": "^1.26.1", + "polytype": "^0.14.0", + "rimraf": "^3.0.2", + "url-join": "^4.0.1", + "xml-js": "^1.6.11", + "yargs": "^17.7.1" + }, + "bin": { + "run": "lib/node_run.js" + } + }, + "node_modules/@amwp/platform-ui-automation/node_modules/node-fetch": { + "version": "2.6.12", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.12.tgz", + "integrity": "sha512-C/fGU2E8ToujUivIO0H+tpQ6HWo4eEmchoPIoXtxCrVghxdKq+QOHqEZW7tuP3KlV3bC8FRMO5nMCC7Zm1VP6g==", + "dev": true, + "dependencies": { + "whatwg-url": "^5.0.0" + }, + "engines": { + "node": "4.x || >=6.0.0" + }, + "peerDependencies": { + "encoding": "^0.1.0" + }, + "peerDependenciesMeta": { + "encoding": { + "optional": true + } + } + }, + "node_modules/@amwp/platform-ui-automation/node_modules/tr46": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", + "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==", + "dev": true + }, + "node_modules/@amwp/platform-ui-automation/node_modules/webidl-conversions": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", + "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==", + "dev": true + }, + "node_modules/@amwp/platform-ui-automation/node_modules/whatwg-url": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", + "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", + "dev": true, + "dependencies": { + "tr46": "~0.0.3", + "webidl-conversions": "^3.0.0" + } + }, + "node_modules/@amwp/platform-ui-lib-adobe": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/@amwp/platform-ui-lib-adobe/-/platform-ui-lib-adobe-0.0.2.tgz", + "integrity": "sha512-Y8TfAPPtk1aoRe0T2Z0G1eClry4lQYDX8w5XOxPfmBWW3KPzOG/t+YYEAlByB6WmLv/mJ6rgxMi1rveJBmKhag==", + "dev": true + }, "node_modules/@babel/code-frame": { "version": "7.18.6", "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.18.6.tgz", @@ -2620,6 +2695,128 @@ "@babel/core": "^7.0.0-0" } }, + "node_modules/@babel/register": { + "version": "7.17.0", + "resolved": "https://registry.npmjs.org/@babel/register/-/register-7.17.0.tgz", + "integrity": "sha512-UNZsMAZ7uKoGHo1HlEXfteEOYssf64n/PNLHGqOKq/bgYcu/4LrQWAHJwSCb3BRZK8Hi5gkJdRcwrGTO2wtRCg==", + "dev": true, + "dependencies": { + "clone-deep": "^4.0.1", + "find-cache-dir": "^2.0.0", + "make-dir": "^2.1.0", + "pirates": "^4.0.5", + "source-map-support": "^0.5.16" + }, + "engines": { + "node": ">=6.9.0" + }, + "peerDependencies": { + "@babel/core": "^7.0.0-0" + } + }, + "node_modules/@babel/register/node_modules/find-cache-dir": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-cache-dir/-/find-cache-dir-2.1.0.tgz", + "integrity": "sha512-Tq6PixE0w/VMFfCgbONnkiQIVol/JJL7nRMi20fqzA4NRs9AfeqMGeRdPi3wIhYkxjeBaWh2rxwapn5Tu3IqOQ==", + "dev": true, + "dependencies": { + "commondir": "^1.0.1", + "make-dir": "^2.0.0", + "pkg-dir": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/register/node_modules/find-up": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-3.0.0.tgz", + "integrity": "sha512-1yD6RmLI1XBfxugvORwlck6f75tYL+iR0jqwsOrOxMZyGYqUuDhJ0l4AXdO1iX/FTs9cBAMEk1gWSEx1kSbylg==", + "dev": true, + "dependencies": { + "locate-path": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/register/node_modules/locate-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-3.0.0.tgz", + "integrity": "sha512-7AO748wWnIhNqAuaty2ZWHkQHRSNfPVIsPIfwEOWO22AmaoVrWavlOcMR5nzTLNYvp36X220/maaRsrec1G65A==", + "dev": true, + "dependencies": { + "p-locate": "^3.0.0", + "path-exists": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/register/node_modules/make-dir": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-2.1.0.tgz", + "integrity": "sha512-LS9X+dc8KLxXCb8dni79fLIIUA5VyZoyjSMCwTluaXA0o27cCK0bhXkpgw+sTXVpPy/lSO57ilRixqk0vDmtRA==", + "dev": true, + "dependencies": { + "pify": "^4.0.1", + "semver": "^5.6.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/register/node_modules/p-locate": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-3.0.0.tgz", + "integrity": "sha512-x+12w/To+4GFfgJhBEpiDcLozRJGegY+Ei7/z0tSLkMmxGZNybVMSfWj9aJn8Z5Fc7dBUNJOOVgPv2H7IwulSQ==", + "dev": true, + "dependencies": { + "p-limit": "^2.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/register/node_modules/path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha512-bpC7GYwiDYQ4wYLe+FA8lhRjhQCMcQGuSgGGqDkg/QerRWw9CmGRT0iSOVRSZJ29NMLZgIzqaljJ63oaL4NIJQ==", + "dev": true, + "engines": { + "node": ">=4" + } + }, + "node_modules/@babel/register/node_modules/pify": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/pify/-/pify-4.0.1.tgz", + "integrity": "sha512-uB80kBFb/tfd68bVleG9T5GGsGPjJrLAUpR5PZIrhBnIaRTQRjqdJSsIKkOP6OAIFbj7GOrcudc5pNjZ+geV2g==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/register/node_modules/pkg-dir": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-3.0.0.tgz", + "integrity": "sha512-/E57AYkoeQ25qkxMj5PBOVgF8Kiu/h7cYS30Z5+R7WaiCCBfLq58ZI/dSeaEKb9WVJV5n/03QwrN3IeWIFllvw==", + "dev": true, + "dependencies": { + "find-up": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/@babel/register/node_modules/semver": { + "version": "5.7.2", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.2.tgz", + "integrity": "sha512-cBznnQ9KjJqU67B52RMC65CMarK2600WFnbkcaiwWq3xy/5haFJlshgnpjovMVJ+Hff49d8GEn0b87C5pDQ10g==", + "dev": true, + "bin": { + "semver": "bin/semver" + } + }, "node_modules/@babel/runtime": { "version": "7.20.1", "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.20.1.tgz", @@ -2687,6 +2884,433 @@ "integrity": "sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw==", "dev": true }, + "node_modules/@colors/colors": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/@colors/colors/-/colors-1.5.0.tgz", + "integrity": "sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==", + "dev": true, + "optional": true, + "engines": { + "node": ">=0.1.90" + } + }, + "node_modules/@cucumber/ci-environment": { + "version": "9.1.0", + "resolved": "https://registry.npmjs.org/@cucumber/ci-environment/-/ci-environment-9.1.0.tgz", + "integrity": "sha512-jdnF6APXP3GawMue8kdMxhu6TBhyRUO4KDRxTowf06NtclLjIw2Ybpo9IcIOMvE8kHukvJyM00uxWX+CfS7JgQ==", + "dev": true + }, + "node_modules/@cucumber/cucumber": { + "version": "8.11.1", + "resolved": "https://registry.npmjs.org/@cucumber/cucumber/-/cucumber-8.11.1.tgz", + "integrity": "sha512-C+wdypoSzHA48GCRorJCAZYuxXo1RSESukAmoz/JhGV7KB4pIlg9Y2aWeZKx6bJQkq8yq4+S4jg9f8FGCdc3jQ==", + "dev": true, + "dependencies": { + "@cucumber/ci-environment": "9.1.0", + "@cucumber/cucumber-expressions": "16.1.1", + "@cucumber/gherkin": "26.0.3", + "@cucumber/gherkin-streams": "5.0.1", + "@cucumber/gherkin-utils": "8.0.2", + "@cucumber/html-formatter": "20.2.1", + "@cucumber/message-streams": "4.0.1", + "@cucumber/messages": "21.0.1", + "@cucumber/tag-expressions": "5.0.1", + "assertion-error-formatter": "^3.0.0", + "capital-case": "^1.0.4", + "chalk": "^4.1.2", + "cli-table3": "0.6.3", + "commander": "^9.0.0", + "debug": "^4.3.4", + "error-stack-parser": "^2.1.4", + "figures": "^3.2.0", + "glob": "^7.1.6", + "has-ansi": "^4.0.1", + "indent-string": "^4.0.0", + "is-installed-globally": "^0.4.0", + "is-stream": "^2.0.0", + "knuth-shuffle-seeded": "^1.0.6", + "lodash.merge": "^4.6.2", + "lodash.mergewith": "^4.6.2", + "luxon": "3.2.1", + "mz": "^2.7.0", + "progress": "^2.0.3", + "resolve-pkg": "^2.0.0", + "semver": "7.3.8", + "string-argv": "^0.3.1", + "strip-ansi": "6.0.1", + "supports-color": "^8.1.1", + "tmp": "^0.2.1", + "util-arity": "^1.1.0", + "verror": "^1.10.0", + "xmlbuilder": "^15.1.1", + "yaml": "1.10.2", + "yup": "^0.32.11" + }, + "bin": { + "cucumber-js": "bin/cucumber.js" + }, + "engines": { + "node": "12 || 14 || >=16" + } + }, + "node_modules/@cucumber/cucumber-expressions": { + "version": "16.1.1", + "resolved": "https://registry.npmjs.org/@cucumber/cucumber-expressions/-/cucumber-expressions-16.1.1.tgz", + "integrity": "sha512-Ugsb9qxfgrgfUKsGvbx0awVk+69NIFjWfxNT+dnm62YrF2gdTHYxAOzOLuPgvE0yqYTh+3otrFLDDfkHGThM1g==", + "dev": true, + "dependencies": { + "regexp-match-indices": "1.0.2" + } + }, + "node_modules/@cucumber/cucumber/node_modules/@cucumber/messages": { + "version": "21.0.1", + "resolved": "https://registry.npmjs.org/@cucumber/messages/-/messages-21.0.1.tgz", + "integrity": "sha512-pGR7iURM4SF9Qp1IIpNiVQ77J9kfxMkPOEbyy+zRmGABnWWCsqMpJdfHeh9Mb3VskemVw85++e15JT0PYdcR3g==", + "dev": true, + "dependencies": { + "@types/uuid": "8.3.4", + "class-transformer": "0.5.1", + "reflect-metadata": "0.1.13", + "uuid": "9.0.0" + } + }, + "node_modules/@cucumber/cucumber/node_modules/@types/uuid": { + "version": "8.3.4", + "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-8.3.4.tgz", + "integrity": "sha512-c/I8ZRb51j+pYGAu5CrFMRxqZ2ke4y2grEBO5AUjgSkSk+qT2Ea+OdWElz/OiMf5MNpn2b17kuVBwZLQJXzihw==", + "dev": true + }, + "node_modules/@cucumber/cucumber/node_modules/ansi-regex": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.1.tgz", + "integrity": "sha512-ILlv4k/3f6vfQ4OoP2AGvirOktlQ98ZEL1k9FaQjxa3L1abBgbuTDAdPOpvbGncC0BTVQrl+OM8xZGK6tWXt7g==", + "dev": true, + "engines": { + "node": ">=6" + } + }, + "node_modules/@cucumber/cucumber/node_modules/ansi-styles": { + "version": "4.3.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-4.3.0.tgz", + "integrity": "sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==", + "dev": true, + "dependencies": { + "color-convert": "^2.0.1" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/@cucumber/cucumber/node_modules/chalk": { + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.2.tgz", + "integrity": "sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==", + "dev": true, + "dependencies": { + "ansi-styles": "^4.1.0", + "supports-color": "^7.1.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/chalk?sponsor=1" + } + }, + "node_modules/@cucumber/cucumber/node_modules/chalk/node_modules/supports-color": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-7.2.0.tgz", + "integrity": "sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/@cucumber/cucumber/node_modules/color-convert": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-2.0.1.tgz", + "integrity": "sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==", + "dev": true, + "dependencies": { + "color-name": "~1.1.4" + }, + "engines": { + "node": ">=7.0.0" + } + }, + "node_modules/@cucumber/cucumber/node_modules/color-name": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", + "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==", + "dev": true + }, + "node_modules/@cucumber/cucumber/node_modules/commander": { + "version": "9.5.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-9.5.0.tgz", + "integrity": "sha512-KRs7WVDKg86PWiuAqhDrAQnTXZKraVcCc6vFdL14qrZ/DcWwuRo7VoiYXalXO7S5GKpqYiVEwCbgFDfxNHKJBQ==", + "dev": true, + "engines": { + "node": "^12.20.0 || >=14" + } + }, + "node_modules/@cucumber/cucumber/node_modules/figures": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", + "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", + "dev": true, + "dependencies": { + "escape-string-regexp": "^1.0.5" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@cucumber/cucumber/node_modules/has-ansi": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-4.0.1.tgz", + "integrity": "sha512-Qr4RtTm30xvEdqUXbSBVWDu+PrTokJOwe/FU+VdfJPk+MXAPoeOzKpRyrDTnZIJwAkQ4oBLTU53nu0HrkF/Z2A==", + "dev": true, + "dependencies": { + "ansi-regex": "^4.1.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/@cucumber/cucumber/node_modules/has-flag": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz", + "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, + "node_modules/@cucumber/cucumber/node_modules/semver": { + "version": "7.3.8", + "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz", + "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==", + "dev": true, + "dependencies": { + "lru-cache": "^6.0.0" + }, + "bin": { + "semver": "bin/semver.js" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/@cucumber/cucumber/node_modules/supports-color": { + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz", + "integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==", + "dev": true, + "dependencies": { + "has-flag": "^4.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/supports-color?sponsor=1" + } + }, + "node_modules/@cucumber/gherkin": { + "version": "26.0.3", + "resolved": "https://registry.npmjs.org/@cucumber/gherkin/-/gherkin-26.0.3.tgz", + "integrity": "sha512-xwJHi//bLFEU1drIyw2yswwUHnnVWO4XcyVBbCTDs6DkSh262GkogFI/IWwChZqJfOXnPglzLGxR1DibcZsILA==", + "dev": true, + "dependencies": { + "@cucumber/messages": "19.1.4 - 21" + } + }, + "node_modules/@cucumber/gherkin-streams": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/@cucumber/gherkin-streams/-/gherkin-streams-5.0.1.tgz", + "integrity": "sha512-/7VkIE/ASxIP/jd4Crlp4JHXqdNFxPGQokqWqsaCCiqBiu5qHoKMxcWNlp9njVL/n9yN4S08OmY3ZR8uC5x74Q==", + "dev": true, + "dependencies": { + "commander": "9.1.0", + "source-map-support": "0.5.21" + }, + "bin": { + "gherkin-javascript": "bin/gherkin" + }, + "peerDependencies": { + "@cucumber/gherkin": ">=22.0.0", + "@cucumber/message-streams": ">=4.0.0", + "@cucumber/messages": ">=17.1.1" + } + }, + "node_modules/@cucumber/gherkin-streams/node_modules/commander": { + "version": "9.1.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-9.1.0.tgz", + "integrity": "sha512-i0/MaqBtdbnJ4XQs4Pmyb+oFQl+q0lsAmokVUH92SlSw4fkeAcG3bVon+Qt7hmtF+u3Het6o4VgrcY3qAoEB6w==", + "dev": true, + "engines": { + "node": "^12.20.0 || >=14" + } + }, + "node_modules/@cucumber/gherkin-utils": { + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/@cucumber/gherkin-utils/-/gherkin-utils-8.0.2.tgz", + "integrity": "sha512-aQlziN3r3cTwprEDbLEcFoMRQajb9DTOu2OZZp5xkuNz6bjSTowSY90lHUD2pWT7jhEEckZRIREnk7MAwC2d1A==", + "dev": true, + "dependencies": { + "@cucumber/gherkin": "^25.0.0", + "@cucumber/messages": "^19.1.4", + "@teppeis/multimaps": "2.0.0", + "commander": "9.4.1", + "source-map-support": "^0.5.21" + }, + "bin": { + "gherkin-utils": "bin/gherkin-utils" + } + }, + "node_modules/@cucumber/gherkin-utils/node_modules/@cucumber/gherkin": { + "version": "25.0.2", + "resolved": "https://registry.npmjs.org/@cucumber/gherkin/-/gherkin-25.0.2.tgz", + "integrity": "sha512-EdsrR33Y5GjuOoe2Kq5Y9DYwgNRtUD32H4y2hCrT6+AWo7ibUQu7H+oiWTgfVhwbkHsZmksxHSxXz/AwqqyCRQ==", + "dev": true, + "dependencies": { + "@cucumber/messages": "^19.1.4" + } + }, + "node_modules/@cucumber/gherkin-utils/node_modules/@cucumber/messages": { + "version": "19.1.4", + "resolved": "https://registry.npmjs.org/@cucumber/messages/-/messages-19.1.4.tgz", + "integrity": "sha512-Pksl0pnDz2l1+L5Ug85NlG6LWrrklN9qkMxN5Mv+1XZ3T6u580dnE6mVaxjJRdcOq4tR17Pc0RqIDZMyVY1FlA==", + "dev": true, + "dependencies": { + "@types/uuid": "8.3.4", + "class-transformer": "0.5.1", + "reflect-metadata": "0.1.13", + "uuid": "9.0.0" + } + }, + "node_modules/@cucumber/gherkin-utils/node_modules/@types/uuid": { + "version": "8.3.4", + "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-8.3.4.tgz", + "integrity": "sha512-c/I8ZRb51j+pYGAu5CrFMRxqZ2ke4y2grEBO5AUjgSkSk+qT2Ea+OdWElz/OiMf5MNpn2b17kuVBwZLQJXzihw==", + "dev": true + }, + "node_modules/@cucumber/gherkin-utils/node_modules/commander": { + "version": "9.4.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-9.4.1.tgz", + "integrity": "sha512-5EEkTNyHNGFPD2H+c/dXXfQZYa/scCKasxWcXJaWnNJ99pnQN9Vnmqow+p+PlFPE63Q6mThaZws1T+HxfpgtPw==", + "dev": true, + "engines": { + "node": "^12.20.0 || >=14" + } + }, + "node_modules/@cucumber/gherkin/node_modules/@cucumber/messages": { + "version": "21.0.1", + "resolved": "https://registry.npmjs.org/@cucumber/messages/-/messages-21.0.1.tgz", + "integrity": "sha512-pGR7iURM4SF9Qp1IIpNiVQ77J9kfxMkPOEbyy+zRmGABnWWCsqMpJdfHeh9Mb3VskemVw85++e15JT0PYdcR3g==", + "dev": true, + "dependencies": { + "@types/uuid": "8.3.4", + "class-transformer": "0.5.1", + "reflect-metadata": "0.1.13", + "uuid": "9.0.0" + } + }, + "node_modules/@cucumber/gherkin/node_modules/@types/uuid": { + "version": "8.3.4", + "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-8.3.4.tgz", + "integrity": "sha512-c/I8ZRb51j+pYGAu5CrFMRxqZ2ke4y2grEBO5AUjgSkSk+qT2Ea+OdWElz/OiMf5MNpn2b17kuVBwZLQJXzihw==", + "dev": true + }, + "node_modules/@cucumber/html-formatter": { + "version": "20.2.1", + "resolved": "https://registry.npmjs.org/@cucumber/html-formatter/-/html-formatter-20.2.1.tgz", + "integrity": "sha512-bwwyr1WjlOJ5dEFOLGbtYWbUprloB2eymqXBmmTC10s0xapZXkFn4VfHgMshaH91XiCIY/MoabWNAau3AeMHkQ==", + "dev": true, + "peerDependencies": { + "@cucumber/messages": ">=18" + } + }, + "node_modules/@cucumber/message-streams": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/@cucumber/message-streams/-/message-streams-4.0.1.tgz", + "integrity": "sha512-Kxap9uP5jD8tHUZVjTWgzxemi/0uOsbGjd4LBOSxcJoOCRbESFwemUzilJuzNTB8pcTQUh8D5oudUyxfkJOKmA==", + "dev": true, + "peerDependencies": { + "@cucumber/messages": ">=17.1.1" + } + }, + "node_modules/@cucumber/messages": { + "version": "22.0.0", + "resolved": "https://registry.npmjs.org/@cucumber/messages/-/messages-22.0.0.tgz", + "integrity": "sha512-EuaUtYte9ilkxcKmfqGF9pJsHRUU0jwie5ukuZ/1NPTuHS1LxHPsGEODK17RPRbZHOFhqybNzG2rHAwThxEymg==", + "dev": true, + "peer": true, + "dependencies": { + "@types/uuid": "9.0.1", + "class-transformer": "0.5.1", + "reflect-metadata": "0.1.13", + "uuid": "9.0.0" + } + }, + "node_modules/@cucumber/pretty-formatter": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@cucumber/pretty-formatter/-/pretty-formatter-1.0.0.tgz", + "integrity": "sha512-wcnIMN94HyaHGsfq72dgCvr1d8q6VGH4Y6Gl5weJ2TNZw1qn2UY85Iki4c9VdaLUONYnyYH3+178YB+9RFe/Hw==", + "dev": true, + "dependencies": { + "ansi-styles": "^5.0.0", + "cli-table3": "^0.6.0", + "figures": "^3.2.0", + "ts-dedent": "^2.0.0" + }, + "peerDependencies": { + "@cucumber/cucumber": ">=7.0.0", + "@cucumber/messages": "*" + } + }, + "node_modules/@cucumber/pretty-formatter/node_modules/ansi-styles": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-5.2.0.tgz", + "integrity": "sha512-Cxwpt2SfTzTtXcfOlzGEee8O+c+MmUgGrNiBcXnuWxuFJHe6a5Hz7qwhwe5OgaSYI0IJvkLqWX1ASG+cJOkEiA==", + "dev": true, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/chalk/ansi-styles?sponsor=1" + } + }, + "node_modules/@cucumber/pretty-formatter/node_modules/figures": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-3.2.0.tgz", + "integrity": "sha512-yaduQFRKLXYOGgEn6AZau90j3ggSOyiqXU0F9JZfeXYhNa+Jk4X+s45A2zg5jns87GAFa34BBm2kXw4XpNcbdg==", + "dev": true, + "dependencies": { + "escape-string-regexp": "^1.0.5" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/@cucumber/tag-expressions": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/@cucumber/tag-expressions/-/tag-expressions-5.0.1.tgz", + "integrity": "sha512-N43uWud8ZXuVjza423T9ZCIJsaZhFekmakt7S9bvogTxqdVGbRobjR663s0+uW0Rz9e+Pa8I6jUuWtoBLQD2Mw==", + "dev": true + }, "node_modules/@eslint/eslintrc": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.4.1.tgz", @@ -3639,6 +4263,25 @@ "node": ">= 8" } }, + "node_modules/@playwright/test": { + "version": "1.37.0", + "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.37.0.tgz", + "integrity": "sha512-181WBLk4SRUyH1Q96VZl7BP6HcK0b7lbdeKisn3N/vnjitk+9HbdlFz/L5fey05vxaAhldIDnzo8KUoy8S3mmQ==", + "dev": true, + "dependencies": { + "@types/node": "*", + "playwright-core": "1.37.0" + }, + "bin": { + "playwright": "cli.js" + }, + "engines": { + "node": ">=16" + }, + "optionalDependencies": { + "fsevents": "2.3.2" + } + }, "node_modules/@rollup/plugin-alias": { "version": "3.1.9", "resolved": "https://registry.npmjs.org/@rollup/plugin-alias/-/plugin-alias-3.1.9.tgz", @@ -3806,6 +4449,15 @@ "string.prototype.matchall": "^4.0.6" } }, + "node_modules/@teppeis/multimaps": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@teppeis/multimaps/-/multimaps-2.0.0.tgz", + "integrity": "sha512-TL1adzq1HdxUf9WYduLcQ/DNGYiz71U31QRgbnr0Ef1cPyOUOsBojxHVWpFeOSUucB6Lrs0LxFRA14ntgtkc9w==", + "dev": true, + "engines": { + "node": ">=10.17" + } + }, "node_modules/@tootallnate/once": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/@tootallnate/once/-/once-2.0.0.tgz", @@ -4097,6 +4749,12 @@ "@types/koa": "*" } }, + "node_modules/@types/lodash": { + "version": "4.14.197", + "resolved": "https://registry.npmjs.org/@types/lodash/-/lodash-4.14.197.tgz", + "integrity": "sha512-BMVOiWs0uNxHVlHBgzTIqJYmj+PgCo4euloGF+5m4okL3rEYzM2EEv78mw8zWSMM57dM7kVIgJ2QDvwHSoCI5g==", + "dev": true + }, "node_modules/@types/mime": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.2.tgz", @@ -4188,6 +4846,13 @@ "integrity": "sha512-Q5vtl1W5ue16D+nIaW8JWebSSraJVlK+EthKn7e7UcD4KWsaSJ8BqGPXNaPghgtcn/fhvrN17Tv8ksUsQpiplw==", "dev": true }, + "node_modules/@types/uuid": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/@types/uuid/-/uuid-9.0.1.tgz", + "integrity": "sha512-rFT3ak0/2trgvp4yYZo5iKFEPsET7vKydKF+VRCxlQ9bpheehyAJH89dAkaLEq/j/RZXJIqcgsmPJKUP1Z28HA==", + "dev": true, + "peer": true + }, "node_modules/@types/ws": { "version": "7.4.7", "resolved": "https://registry.npmjs.org/@types/ws/-/ws-7.4.7.tgz", @@ -4625,6 +5290,12 @@ "node": ">=4" } }, + "node_modules/any-promise": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", + "integrity": "sha512-7UvmKalWRt1wgjL1RrGxoSJW/0QZFIegpeGvZG9kjp8vrRu55XTHbwnqq2GpXm9uLbcuhxm3IqX9OB4MZR1b2A==", + "dev": true + }, "node_modules/anymatch": { "version": "3.1.2", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-3.1.2.tgz", @@ -4708,6 +5379,15 @@ "node": ">=0.10.0" } }, + "node_modules/assert-plus": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", + "integrity": "sha512-NfJ4UzBCcQGLDlQq7nHxH+tv3kyZ0hHQqF5BO6J7tNJeP5do1llPr8dZ8zHonfhAu0PHAdMkSo+8o0wxg9lZWw==", + "dev": true, + "engines": { + "node": ">=0.8" + } + }, "node_modules/assertion-error": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/assertion-error/-/assertion-error-1.1.0.tgz", @@ -4717,6 +5397,26 @@ "node": "*" } }, + "node_modules/assertion-error-formatter": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/assertion-error-formatter/-/assertion-error-formatter-3.0.0.tgz", + "integrity": "sha512-6YyAVLrEze0kQ7CmJfUgrLHb+Y7XghmL2Ie7ijVa2Y9ynP3LV+VDiwFk62Dn0qtqbmY0BT0ss6p1xxpiF2PYbQ==", + "dev": true, + "dependencies": { + "diff": "^4.0.1", + "pad-right": "^0.2.2", + "repeat-string": "^1.6.1" + } + }, + "node_modules/assertion-error-formatter/node_modules/diff": { + "version": "4.0.2", + "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz", + "integrity": "sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==", + "dev": true, + "engines": { + "node": ">=0.3.1" + } + }, "node_modules/astral-regex": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-2.0.0.tgz", @@ -5378,6 +6078,17 @@ } ] }, + "node_modules/capital-case": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/capital-case/-/capital-case-1.0.4.tgz", + "integrity": "sha512-ds37W8CytHgwnhGGTi88pcPyR15qoNkOpYwmMMfnWqqWgESapLqvDx6huFjQ5vqWSn2Z06173XNA7LtMOeUh1A==", + "dev": true, + "dependencies": { + "no-case": "^3.0.4", + "tslib": "^2.0.3", + "upper-case-first": "^2.0.2" + } + }, "node_modules/chai": { "version": "4.3.6", "resolved": "https://registry.npmjs.org/chai/-/chai-4.3.6.tgz", @@ -5512,6 +6223,12 @@ "integrity": "sha512-cOU9usZw8/dXIXKtwa8pM0OTJQuJkxMN6w30csNRUerHfeQ5R6U3kkU/FtJeIf3M202OHfY2U8ccInBG7/xogA==", "dev": true }, + "node_modules/class-transformer": { + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/class-transformer/-/class-transformer-0.5.1.tgz", + "integrity": "sha512-SQa1Ws6hUbfC98vKGxZH3KFY0Y1lm5Zm0SY8XX9zbK7FJCyVEac3ATW0RIpwzW+oOfmHE5PMPufDG9hCfoEOMw==", + "dev": true + }, "node_modules/cli-cursor": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-3.1.0.tgz", @@ -5524,6 +6241,21 @@ "node": ">=8" } }, + "node_modules/cli-table3": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.6.3.tgz", + "integrity": "sha512-w5Jac5SykAeZJKntOxJCrm63Eg5/4dhMWIcuTbo9rpE+brgaSZo0RuNJZeOyMgsUdhDeojvgyQLmjI+K50ZGyg==", + "dev": true, + "dependencies": { + "string-width": "^4.2.0" + }, + "engines": { + "node": "10.* || >= 12.*" + }, + "optionalDependencies": { + "@colors/colors": "1.5.0" + } + }, "node_modules/cliui": { "version": "8.0.1", "resolved": "https://registry.npmjs.org/cliui/-/cliui-8.0.1.tgz", @@ -5597,6 +6329,32 @@ "node": ">=0.8" } }, + "node_modules/clone-deep": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/clone-deep/-/clone-deep-4.0.1.tgz", + "integrity": "sha512-neHB9xuzh/wk0dIHweyAXv2aPGZIVk3pLMe+/RNzINf17fe0OG96QroktYAUm7SM1PBnzTabaLboqqxDyMU+SQ==", + "dev": true, + "dependencies": { + "is-plain-object": "^2.0.4", + "kind-of": "^6.0.2", + "shallow-clone": "^3.0.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/clone-deep/node_modules/is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "dev": true, + "dependencies": { + "isobject": "^3.0.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/clone-regexp": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/clone-regexp/-/clone-regexp-2.2.0.tgz", @@ -5915,6 +6673,12 @@ "browserslist": ">= 4.21.0" } }, + "node_modules/core-util-is": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", + "integrity": "sha512-3lqz5YjWTYnW6dlDa5TLaTCcShfar1e40rmcJVwCBJC6mWlFuj0eCHIElmG1g5kyuJ/GD+8Wn4FFCcz4gJPfaQ==", + "dev": true + }, "node_modules/cosmiconfig": { "version": "7.0.1", "resolved": "https://registry.npmjs.org/cosmiconfig/-/cosmiconfig-7.0.1.tgz", @@ -6550,6 +7314,15 @@ "is-arrayish": "^0.2.1" } }, + "node_modules/error-stack-parser": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/error-stack-parser/-/error-stack-parser-2.1.4.tgz", + "integrity": "sha512-Sk5V6wVazPhq5MhpO+AUxJn5x7XSXGl1R93Vn7i+zS15KDVxQijejNCrz8340/2bgLBjR9GtEG8ZVKONDjcqGQ==", + "dev": true, + "dependencies": { + "stackframe": "^1.3.4" + } + }, "node_modules/errorstacks": { "version": "2.4.0", "resolved": "https://registry.npmjs.org/errorstacks/-/errorstacks-2.4.0.tgz", @@ -7381,6 +8154,15 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/extsprintf": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.4.1.tgz", + "integrity": "sha512-Wrk35e8ydCKDj/ArClo1VrPVmN8zph5V4AtHwIuHhvMXsKf73UT3BOD+azBIW+3wOJ4FhEH7zyaJCFvChjYvMA==", + "dev": true, + "engines": [ + "node >=0.6.0" + ] + }, "node_modules/fast-deep-equal": { "version": "3.1.3", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", @@ -7834,6 +8616,30 @@ "node": ">= 6" } }, + "node_modules/global-dirs": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-3.0.1.tgz", + "integrity": "sha512-NBcGGFbBA9s1VzD41QXDG+3++t9Mn5t1FpLdhESY6oKY4gYTFpX4wO3sqGUa0Srjtbfj3szX0RnemmrVRUdULA==", + "dev": true, + "dependencies": { + "ini": "2.0.0" + }, + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/global-dirs/node_modules/ini": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/ini/-/ini-2.0.0.tgz", + "integrity": "sha512-7PnF4oN3CvZF23ADhA5wRaYEQpJ8qygSkbtTXWBeXWXmEVRXK+1ITciHWwHhsjv1TmW0MgacIv6hEi5pX5NQdA==", + "dev": true, + "engines": { + "node": ">=10" + } + }, "node_modules/global-modules": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-2.0.0.tgz", @@ -8045,6 +8851,15 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/he": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/he/-/he-1.2.0.tgz", + "integrity": "sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==", + "dev": true, + "bin": { + "he": "bin/he" + } + }, "node_modules/hosted-git-info": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-4.1.0.tgz", @@ -8436,6 +9251,18 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/is-ci": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-3.0.1.tgz", + "integrity": "sha512-ZYvCgrefwqoQ6yTyYUbQu64HsITZ3NfKX1lzaEYdkTDcfKzzCI/wthRRYKkdjHKFVgNiXKAKm65Zo1pk2as/QQ==", + "dev": true, + "dependencies": { + "ci-info": "^3.2.0" + }, + "bin": { + "is-ci": "bin.js" + } + }, "node_modules/is-core-module": { "version": "2.9.0", "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.9.0.tgz", @@ -8526,10 +9353,26 @@ "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", "dev": true, "dependencies": { - "is-extglob": "^2.1.1" + "is-extglob": "^2.1.1" + }, + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/is-installed-globally": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.4.0.tgz", + "integrity": "sha512-iwGqO3J21aaSkC7jWnHP/difazwS7SFeIqxv6wEtLU8Y5KlzFTjyqcSIT0d8s4+dDhKytsk9PJZ2BkS5eZwQRQ==", + "dev": true, + "dependencies": { + "global-dirs": "^3.0.0", + "is-path-inside": "^3.0.2" }, "engines": { - "node": ">=0.10.0" + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" } }, "node_modules/is-module": { @@ -8574,6 +9417,15 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/is-path-inside": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-3.0.3.tgz", + "integrity": "sha512-Fd4gABb+ycGAmKou8eMftCupSir5lRxqf4aD/vd0cD2qc4HL07OjCeuHMr8Ro4CoMaeCKDB0/ECBOVWjTwUvPQ==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/is-plain-obj": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", @@ -8734,6 +9586,15 @@ "integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==", "dev": true }, + "node_modules/isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha512-WhB9zCku7EGTj/HQQRz5aUQEUeoQZH2bWcltRErOpymJ4boYE6wL9Tbr23krRPSZ+C5zqNSrSw+Cc7sZZ4b7vg==", + "dev": true, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/istanbul-lib-coverage": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/istanbul-lib-coverage/-/istanbul-lib-coverage-3.2.0.tgz", @@ -10843,6 +11704,15 @@ "integrity": "sha512-RTSoaUAfLvpR357vWzAz/50Q/BmHfmE6ETSWfutT0AJiw10e6CmcdYRQJlLRd95B53D0Y2aD1jSxD3V3ySF+PA==", "dev": true }, + "node_modules/knuth-shuffle-seeded": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/knuth-shuffle-seeded/-/knuth-shuffle-seeded-1.0.6.tgz", + "integrity": "sha512-9pFH0SplrfyKyojCLxZfMcvkhf5hH0d+UwR9nTVJ/DDQJGuzcXjTwB7TP7sDfehSudlGGaOLblmEWqv04ERVWg==", + "dev": true, + "dependencies": { + "seed-random": "~2.2.0" + } + }, "node_modules/koa": { "version": "2.13.4", "resolved": "https://registry.npmjs.org/koa/-/koa-2.13.4.tgz", @@ -11030,6 +11900,12 @@ "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==", "dev": true }, + "node_modules/lodash-es": { + "version": "4.17.21", + "resolved": "https://registry.npmjs.org/lodash-es/-/lodash-es-4.17.21.tgz", + "integrity": "sha512-mKnC+QJ9pWVzv+C4/U3rRsHapFfHvQFoFB92e52xeyGMcX6/OlIl78je1u8vePzYZSkkogMPJ2yjxxsb89cxyw==", + "dev": true + }, "node_modules/lodash.camelcase": { "version": "4.3.0", "resolved": "https://registry.npmjs.org/lodash.camelcase/-/lodash.camelcase-4.3.0.tgz", @@ -11060,6 +11936,12 @@ "integrity": "sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==", "dev": true }, + "node_modules/lodash.mergewith": { + "version": "4.6.2", + "resolved": "https://registry.npmjs.org/lodash.mergewith/-/lodash.mergewith-4.6.2.tgz", + "integrity": "sha512-GK3g5RPZWTRSeLSpgP8Xhra+pnjBC56q9FZYe1d5RN3TJ35dbkGy3YqBSMbyCrlbi+CM9Z3Jk5yTL7RCsqboyQ==", + "dev": true + }, "node_modules/lodash.truncate": { "version": "4.4.2", "resolved": "https://registry.npmjs.org/lodash.truncate/-/lodash.truncate-4.4.2.tgz", @@ -11099,6 +11981,15 @@ "get-func-name": "^2.0.0" } }, + "node_modules/lower-case": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/lower-case/-/lower-case-2.0.2.tgz", + "integrity": "sha512-7fm3l3NAF9WfN6W3JOmf5drwpVqX78JtoGJ3A6W0a6ZnldM41w2fV5D490psKFTpMds8TJse/eHLFFsNHHjHgg==", + "dev": true, + "dependencies": { + "tslib": "^2.0.3" + } + }, "node_modules/lru-cache": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-6.0.0.tgz", @@ -11111,6 +12002,15 @@ "node": ">=10" } }, + "node_modules/luxon": { + "version": "3.2.1", + "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.2.1.tgz", + "integrity": "sha512-QrwPArQCNLAKGO/C+ZIilgIuDnEnKx5QYODdDtbFaxzsbZcc/a7WFq7MhsVYgRlwawLtvOUESTlfJ+hc/USqPg==", + "dev": true, + "engines": { + "node": ">=12" + } + }, "node_modules/magic-string": { "version": "0.25.9", "resolved": "https://registry.npmjs.org/magic-string/-/magic-string-0.25.9.tgz", @@ -11536,6 +12436,23 @@ "integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w==", "dev": true }, + "node_modules/mz": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/mz/-/mz-2.7.0.tgz", + "integrity": "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==", + "dev": true, + "dependencies": { + "any-promise": "^1.0.0", + "object-assign": "^4.0.1", + "thenify-all": "^1.0.0" + } + }, + "node_modules/nanoclone": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/nanoclone/-/nanoclone-0.2.1.tgz", + "integrity": "sha512-wynEP02LmIbLpcYw8uBKpcfF6dmg2vcpKqxeH5UcoKEYdExslsdUA4ugFauuaeYdTB76ez6gJW8XAZ6CgkXYxA==", + "dev": true + }, "node_modules/nanocolors": { "version": "0.2.13", "resolved": "https://registry.npmjs.org/nanocolors/-/nanocolors-0.2.13.tgz", @@ -11582,6 +12499,16 @@ "path-to-regexp": "^1.7.0" } }, + "node_modules/no-case": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/no-case/-/no-case-3.0.4.tgz", + "integrity": "sha512-fgAN3jGAh+RoxUGZHTSOLJIqUc2wmoBwGR4tbpNAKmmovFoWq0OdRkb0VkldReO2a2iBT/OEulG9XSUc10r3zg==", + "dev": true, + "dependencies": { + "lower-case": "^2.0.2", + "tslib": "^2.0.3" + } + }, "node_modules/node-fetch": { "version": "2.6.7", "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.7.tgz", @@ -11624,6 +12551,87 @@ "webidl-conversions": "^3.0.0" } }, + "node_modules/node-html-parser": { + "version": "6.1.5", + "resolved": "https://registry.npmjs.org/node-html-parser/-/node-html-parser-6.1.5.tgz", + "integrity": "sha512-fAaM511feX++/Chnhe475a0NHD8M7AxDInsqQpz6x63GRF7xYNdS8Vo5dKsIVPgsOvG7eioRRTZQnWBrhDHBSg==", + "dev": true, + "dependencies": { + "css-select": "^5.1.0", + "he": "1.2.0" + } + }, + "node_modules/node-html-parser/node_modules/css-select": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/css-select/-/css-select-5.1.0.tgz", + "integrity": "sha512-nwoRF1rvRRnnCqqY7updORDsuqKzqYJ28+oSMaJMMgOauh3fvwHqMS7EZpIPqK8GL+g9mKxF1vP/ZjSeNjEVHg==", + "dev": true, + "dependencies": { + "boolbase": "^1.0.0", + "css-what": "^6.1.0", + "domhandler": "^5.0.2", + "domutils": "^3.0.1", + "nth-check": "^2.0.1" + }, + "funding": { + "url": "https://github.com/sponsors/fb55" + } + }, + "node_modules/node-html-parser/node_modules/dom-serializer": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/dom-serializer/-/dom-serializer-2.0.0.tgz", + "integrity": "sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==", + "dev": true, + "dependencies": { + "domelementtype": "^2.3.0", + "domhandler": "^5.0.2", + "entities": "^4.2.0" + }, + "funding": { + "url": "https://github.com/cheeriojs/dom-serializer?sponsor=1" + } + }, + "node_modules/node-html-parser/node_modules/domhandler": { + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/domhandler/-/domhandler-5.0.3.tgz", + "integrity": "sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w==", + "dev": true, + "dependencies": { + "domelementtype": "^2.3.0" + }, + "engines": { + "node": ">= 4" + }, + "funding": { + "url": "https://github.com/fb55/domhandler?sponsor=1" + } + }, + "node_modules/node-html-parser/node_modules/domutils": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/domutils/-/domutils-3.1.0.tgz", + "integrity": "sha512-H78uMmQtI2AhgDJjWeQmHwJJ2bLPD3GMmO7Zja/ZZh84wkm+4ut+IUnUdRa8uCGX88DiVx1j6FRe1XfxEgjEZA==", + "dev": true, + "dependencies": { + "dom-serializer": "^2.0.0", + "domelementtype": "^2.3.0", + "domhandler": "^5.0.3" + }, + "funding": { + "url": "https://github.com/fb55/domutils?sponsor=1" + } + }, + "node_modules/node-html-parser/node_modules/entities": { + "version": "4.5.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz", + "integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==", + "dev": true, + "engines": { + "node": ">=0.12" + }, + "funding": { + "url": "https://github.com/fb55/entities?sponsor=1" + } + }, "node_modules/node-int64": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/node-int64/-/node-int64-0.4.0.tgz", @@ -11966,6 +12974,18 @@ "node": ">=6" } }, + "node_modules/pad-right": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/pad-right/-/pad-right-0.2.2.tgz", + "integrity": "sha512-4cy8M95ioIGolCoMmm2cMntGR1lPLEbOMzOKu8bzjuJP6JpzEMQcDHmh7hHLYGgob+nKe1YHFMaG4V59HQa89g==", + "dev": true, + "dependencies": { + "repeat-string": "^1.5.2" + }, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/parent-module": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", @@ -12128,6 +13148,43 @@ "node": ">=8" } }, + "node_modules/playwright": { + "version": "1.37.0", + "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.37.0.tgz", + "integrity": "sha512-CrAEFfVioamMwDKmygc/HAkzEAxYAwjD+zod2poTxM7ObivkoDsKHu1ned16fnQV/Tf1kDB8KtsyH8Qd3VzJIg==", + "dev": true, + "hasInstallScript": true, + "dependencies": { + "playwright-core": "1.37.0" + }, + "bin": { + "playwright": "cli.js" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/playwright-core": { + "version": "1.37.0", + "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.37.0.tgz", + "integrity": "sha512-1c46jhTH/myQw6sesrcuHVtLoSNfJv8Pfy9t3rs6subY7kARv0HRw5PpyfPYPpPtQvBOmgbE6K+qgYUpj81LAA==", + "dev": true, + "bin": { + "playwright-core": "cli.js" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/polytype": { + "version": "0.14.1", + "resolved": "https://registry.npmjs.org/polytype/-/polytype-0.14.1.tgz", + "integrity": "sha512-+ZV9fvmSOTojIbvlUaLebkpzfSn+9ZsETaopIyE7SCBBc8EKUf6JAPpiGh4VlQJ+Vo71AOZjEVviTQndWAXc4A==", + "dev": true, + "engines": { + "node": ">=14.0.0" + } + }, "node_modules/portfinder": { "version": "1.0.28", "resolved": "https://registry.npmjs.org/portfinder/-/portfinder-1.0.28.tgz", @@ -13201,6 +14258,12 @@ "node": ">=6" } }, + "node_modules/property-expr": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/property-expr/-/property-expr-2.0.5.tgz", + "integrity": "sha512-IJUkICM5dP5znhCckHSv30Q4b5/JA5enCtkRHYaOVOAocnH/1BQEYTC5NMfT3AVl/iXKdr3aqQbQn9DxyWknwA==", + "dev": true + }, "node_modules/proxy-from-env": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", @@ -13522,6 +14585,12 @@ "node": ">=6" } }, + "node_modules/reflect-metadata": { + "version": "0.1.13", + "resolved": "https://registry.npmjs.org/reflect-metadata/-/reflect-metadata-0.1.13.tgz", + "integrity": "sha512-Ts1Y/anZELhSsjMcU605fU9RE4Oi3p5ORujwbIKXfWa+0Zxs510Qrmrce5/Jowq3cHSZSJqBjypxmHarc+vEWg==", + "dev": true + }, "node_modules/regenerate": { "version": "1.4.2", "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.2.tgz", @@ -13555,6 +14624,24 @@ "@babel/runtime": "^7.8.4" } }, + "node_modules/regexp-match-indices": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/regexp-match-indices/-/regexp-match-indices-1.0.2.tgz", + "integrity": "sha512-DwZuAkt8NF5mKwGGER1EGh2PRqyvhRhhLviH+R8y8dIuaQROlUfXjt4s9ZTXstIsSkptf06BSvwcEmmfheJJWQ==", + "dev": true, + "dependencies": { + "regexp-tree": "^0.1.11" + } + }, + "node_modules/regexp-tree": { + "version": "0.1.27", + "resolved": "https://registry.npmjs.org/regexp-tree/-/regexp-tree-0.1.27.tgz", + "integrity": "sha512-iETxpjK6YoRWJG5o6hXLwvjYAoW+FEZn9os0PD/b6AP6xQwsa/Y7lCVgIixBbUPMfhu+i2LtdeAqVTgGlQarfA==", + "dev": true, + "bin": { + "regexp-tree": "bin/regexp-tree" + } + }, "node_modules/regexp.prototype.flags": { "version": "1.4.3", "resolved": "https://registry.npmjs.org/regexp.prototype.flags/-/regexp.prototype.flags-1.4.3.tgz", @@ -13628,6 +14715,15 @@ "jsesc": "bin/jsesc" } }, + "node_modules/repeat-string": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", + "integrity": "sha512-PV0dzCYDNfRi1jCDbJzpW7jNNDRuCOG/jI5ctQcGKt/clZD+YcPS3yIlWuTJMmESC8aevCFmWJy5wjAFgNqN6w==", + "dev": true, + "engines": { + "node": ">=0.10" + } + }, "node_modules/require-directory": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", @@ -13748,6 +14844,27 @@ "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==", "dev": true }, + "node_modules/resolve-pkg": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/resolve-pkg/-/resolve-pkg-2.0.0.tgz", + "integrity": "sha512-+1lzwXehGCXSeryaISr6WujZzowloigEofRB+dj75y9RRa/obVcYgbHJd53tdYw8pvZj8GojXaaENws8Ktw/hQ==", + "dev": true, + "dependencies": { + "resolve-from": "^5.0.0" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/resolve-pkg/node_modules/resolve-from": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-5.0.0.tgz", + "integrity": "sha512-qYg9KP24dD5qka9J47d0aVky0N+b4fTU89LN9iDnjB5waksiC49rvMB0PrUJQGoTmH50XPiqOvAjDfaijGxYZw==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/resolve.exports": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/resolve.exports/-/resolve.exports-2.0.2.tgz", @@ -14145,6 +15262,12 @@ "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", "dev": true }, + "node_modules/sax": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/sax/-/sax-1.2.4.tgz", + "integrity": "sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==", + "dev": true + }, "node_modules/saxes": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/saxes/-/saxes-6.0.0.tgz", @@ -14157,6 +15280,12 @@ "node": ">=v12.22.7" } }, + "node_modules/seed-random": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/seed-random/-/seed-random-2.2.0.tgz", + "integrity": "sha512-34EQV6AAHQGhoc0tn/96a9Fsi6v2xdqe/dMUwljGRaFOzR3EgRmECvD0O8vi8X+/uQ50LGHfkNu/Eue5TPKZkQ==", + "dev": true + }, "node_modules/semver": { "version": "6.3.0", "resolved": "https://registry.npmjs.org/semver/-/semver-6.3.0.tgz", @@ -14181,6 +15310,18 @@ "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==", "dev": true }, + "node_modules/shallow-clone": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/shallow-clone/-/shallow-clone-3.0.1.tgz", + "integrity": "sha512-/6KqX+GVUdqPuPPd2LxDDxzX6CAbjJehAAOKlNpqqUpAqPM6HeL8f+o3a+JsyGjn2lv0WY8UsTgUJjU9Ok55NA==", + "dev": true, + "dependencies": { + "kind-of": "^6.0.2" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -14445,6 +15586,12 @@ "node": ">=8" } }, + "node_modules/stackframe": { + "version": "1.3.4", + "resolved": "https://registry.npmjs.org/stackframe/-/stackframe-1.3.4.tgz", + "integrity": "sha512-oeVtt7eWQS+Na6F//S4kJ2K2VbRlS9D43mAlMyVpVWovy9o+jfgH8O9agzANzaiLjclA0oYzUXEM4PurhSUChw==", + "dev": true + }, "node_modules/statuses": { "version": "1.5.0", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", @@ -14483,6 +15630,15 @@ } ] }, + "node_modules/string-argv": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/string-argv/-/string-argv-0.3.2.tgz", + "integrity": "sha512-aqD2Q0144Z+/RqG52NeHEkZauTAUWJO8c6yTftGJKO3Tja5tUgIfmIl6kExvhtxSDP7fXB6DvzkfMpCd/F3G+Q==", + "dev": true, + "engines": { + "node": ">=0.6.19" + } + }, "node_modules/string-hash": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/string-hash/-/string-hash-1.1.3.tgz", @@ -15148,6 +16304,27 @@ "integrity": "sha512-N+8UisAXDGk8PFXP4HAzVR9nbfmVJ3zYLAWiTIoqC5v5isinhr+r5uaO8+7r3BMfuNIufIsA7RdpVgacC2cSpw==", "dev": true }, + "node_modules/thenify": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/thenify/-/thenify-3.3.1.tgz", + "integrity": "sha512-RVZSIV5IG10Hk3enotrhvz0T9em6cyHBLkH/YAZuKqd8hRkKhSfCGIcP2KUY0EPxndzANBmNllzWPwak+bheSw==", + "dev": true, + "dependencies": { + "any-promise": "^1.0.0" + } + }, + "node_modules/thenify-all": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/thenify-all/-/thenify-all-1.6.0.tgz", + "integrity": "sha512-RNxQH/qI8/t3thXJDwcstUO4zeqo64+Uy/+sNVRBx4Xn2OX+OZ9oP+iJnNFqplFra2ZUVeKCSa2oVWi3T4uVmA==", + "dev": true, + "dependencies": { + "thenify": ">= 3.1.0 < 4" + }, + "engines": { + "node": ">=0.8" + } + }, "node_modules/through": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", @@ -15164,6 +16341,18 @@ "globrex": "^0.1.2" } }, + "node_modules/tmp": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.2.1.tgz", + "integrity": "sha512-76SUhtfqR2Ijn+xllcI5P1oyannHNHByD80W1q447gU3mp9G9PSpGdWmjUOHRDPiHYacIk66W7ubDTuPF3BEtQ==", + "dev": true, + "dependencies": { + "rimraf": "^3.0.0" + }, + "engines": { + "node": ">=8.17.0" + } + }, "node_modules/tmpl": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/tmpl/-/tmpl-1.0.5.tgz", @@ -15200,6 +16389,12 @@ "node": ">=0.6" } }, + "node_modules/toposort": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/toposort/-/toposort-2.0.2.tgz", + "integrity": "sha512-0a5EOkAUp8D4moMi2W8ZF8jcga7BgZd91O/yabJCFY8az+XSzeGyTKs0Aoo897iV1Nj6guFq8orWDS96z91oGg==", + "dev": true + }, "node_modules/tough-cookie": { "version": "4.1.3", "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-4.1.3.tgz", @@ -15245,6 +16440,15 @@ "node": ">=8" } }, + "node_modules/ts-dedent": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/ts-dedent/-/ts-dedent-2.2.0.tgz", + "integrity": "sha512-q5W7tVM71e2xjHZTlgfTDoPF/SmqKG5hddq9SzR49CH2hayqRKJtQ4mtRlSxKaJlR/+9rEM+mnBHf7I2/BQcpQ==", + "dev": true, + "engines": { + "node": ">=6.10" + } + }, "node_modules/tsconfig-paths": { "version": "3.14.1", "resolved": "https://registry.npmjs.org/tsconfig-paths/-/tsconfig-paths-3.14.1.tgz", @@ -15461,6 +16665,15 @@ "browserslist": ">= 4.21.0" } }, + "node_modules/upper-case-first": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/upper-case-first/-/upper-case-first-2.0.2.tgz", + "integrity": "sha512-514ppYHBaKwfJRK/pNC6c/OxfGa0obSnAl106u97Ed0I625Nin96KAjttZF6ZL3e1XLtphxnqrOi9iWgm+u+bg==", + "dev": true, + "dependencies": { + "tslib": "^2.0.3" + } + }, "node_modules/uri-js": { "version": "4.4.1", "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", @@ -15470,6 +16683,12 @@ "punycode": "^2.1.0" } }, + "node_modules/url-join": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/url-join/-/url-join-4.0.1.tgz", + "integrity": "sha512-jk1+QP6ZJqyOiuEI9AEWQfju/nB2Pw466kbA0LEZljHwKeMgd9WrAEgEGxjPDD2+TNbbb37rTyhEfrCXfuKXnA==", + "dev": true + }, "node_modules/url-parse": { "version": "1.5.10", "resolved": "https://registry.npmjs.org/url-parse/-/url-parse-1.5.10.tgz", @@ -15480,12 +16699,27 @@ "requires-port": "^1.0.0" } }, + "node_modules/util-arity": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/util-arity/-/util-arity-1.1.0.tgz", + "integrity": "sha512-kkyIsXKwemfSy8ZEoaIz06ApApnWsk5hQO0vLjZS6UkBiGiW++Jsyb8vSBoc0WKlffGoGs5yYy/j5pp8zckrFA==", + "dev": true + }, "node_modules/util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", "integrity": "sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==", "dev": true }, + "node_modules/uuid": { + "version": "9.0.0", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.0.tgz", + "integrity": "sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==", + "dev": true, + "bin": { + "uuid": "dist/bin/uuid" + } + }, "node_modules/v8-compile-cache": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz", @@ -15525,6 +16759,20 @@ "node": ">= 0.8" } }, + "node_modules/verror": { + "version": "1.10.1", + "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.1.tgz", + "integrity": "sha512-veufcmxri4e3XSrT0xwfUR7kguIkaxBeosDg00yDWhk49wdwkSUrvvsm7nc75e1PUyvIeZj6nS8VQRYz2/S4Xg==", + "dev": true, + "dependencies": { + "assert-plus": "^1.0.0", + "core-util-is": "1.0.2", + "extsprintf": "^1.2.0" + }, + "engines": { + "node": ">=0.6.0" + } + }, "node_modules/w3c-xmlserializer": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/w3c-xmlserializer/-/w3c-xmlserializer-4.0.0.tgz", @@ -15750,6 +16998,18 @@ } } }, + "node_modules/xml-js": { + "version": "1.6.11", + "resolved": "https://registry.npmjs.org/xml-js/-/xml-js-1.6.11.tgz", + "integrity": "sha512-7rVi2KMfwfWFl+GpPg6m80IVMWXLRjO+PxTq7V2CDhoGak0wzYzFgUY2m4XJ47OGdXd8eLE8EmwfAmdjw7lC1g==", + "dev": true, + "dependencies": { + "sax": "^1.2.4" + }, + "bin": { + "xml-js": "bin/cli.js" + } + }, "node_modules/xml-name-validator": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/xml-name-validator/-/xml-name-validator-4.0.0.tgz", @@ -15759,6 +17019,15 @@ "node": ">=12" } }, + "node_modules/xmlbuilder": { + "version": "15.1.1", + "resolved": "https://registry.npmjs.org/xmlbuilder/-/xmlbuilder-15.1.1.tgz", + "integrity": "sha512-yMqGBqtXyeN1e3TGYvgNgDVZ3j84W4cwkOXQswghol6APgZWaff9lnbvN7MHYJOiXsvGPXtjTYJEiC9J2wv9Eg==", + "dev": true, + "engines": { + "node": ">=8.0" + } + }, "node_modules/xmlchars": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/xmlchars/-/xmlchars-2.2.0.tgz", @@ -15790,9 +17059,9 @@ } }, "node_modules/yargs": { - "version": "17.6.2", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.6.2.tgz", - "integrity": "sha512-1/9UrdHjDZc0eOU0HxOHoS78C69UD3JRMvzlJ7S79S2nTaWRA/whGCTV8o9e/N/1Va9YIV7Q4sOxD8VV4pCWOw==", + "version": "17.7.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-17.7.2.tgz", + "integrity": "sha512-7dSzzRQ++CKnNI/krKnYRV7JKKPUXMEh61soaHKg9mrWEhzFWhFnxPxGl+69cD1Ou63C13NUPCnmIcrvqCuM6w==", "dev": true, "dependencies": { "cliui": "^8.0.1", @@ -15855,6 +17124,24 @@ "funding": { "url": "https://github.com/sponsors/sindresorhus" } + }, + "node_modules/yup": { + "version": "0.32.11", + "resolved": "https://registry.npmjs.org/yup/-/yup-0.32.11.tgz", + "integrity": "sha512-Z2Fe1bn+eLstG8DRR6FTavGD+MeAwyfmouhHsIUgaADz8jvFKbO/fXc2trJKZg+5EBjh4gGm3iU/t3onKlXHIg==", + "dev": true, + "dependencies": { + "@babel/runtime": "^7.15.4", + "@types/lodash": "^4.14.175", + "lodash": "^4.17.21", + "lodash-es": "^4.17.21", + "nanoclone": "^0.2.1", + "property-expr": "^2.0.4", + "toposort": "^2.0.2" + }, + "engines": { + "node": ">=10" + } } } } diff --git a/package.json b/package.json index e9f0a875..43aec1e7 100644 --- a/package.json +++ b/package.json @@ -27,11 +27,14 @@ "homepage": "https://github.com/adobecom/college#readme", "devDependencies": { "@babel/core": "7.17.7", + "@babel/register": "7.17.0", "@babel/eslint-parser": "7.17.0", "@esm-bundle/chai": "4.3.4-fix.0", "@web/dev-server-import-maps": "^0.0.6", "@web/test-runner": "0.13.27", "@web/test-runner-commands": "0.6.1", + "@amwp/platform-ui-automation": "^0.0.2", + "@amwp/platform-ui-lib-adobe": "^0.0.2", "chai": "4.3.6", "eslint": "8.11.0", "eslint-config-airbnb-base": "15.0.0", diff --git a/test/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.jest.js b/test/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.jest.js new file mode 100644 index 00000000..3059920d --- /dev/null +++ b/test/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.jest.js @@ -0,0 +1,135 @@ +/** + * @jest-environment jsdom + */ +import path from 'path'; +import fs from 'fs'; +import init from '../../../acrobat/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb'; + +describe('dc-converter-widget', () => { + beforeEach(async () => { + document.body.innerHTML = fs.readFileSync( + path.resolve(__dirname, './mocks/body.html'), + 'utf8' + ); + window.performance.mark = jest.fn(); + }); + + afterEach(() => { + jest.clearAllMocks(); + }); + + it('loads widget from prod env', async () => { + let fetchUrl = ''; + window.fetch = jest.fn((url) => { + fetchUrl = url; + return Promise.resolve({ + status: 200, + text: () => + Promise.resolve( + fs.readFileSync(path.resolve(__dirname, './mocks/widget.html')) + ), + }); + }); + delete window.location; + window.location = new URL('https://www.adobe.com'); + const block = document.querySelector('.dc-converter-widget-ootb'); + const widget = await init(block); + document.dispatchEvent(new Event('milo:deferred')); + const launcher = document.querySelector('#adobe_dc_sdk_launcher'); + expect(launcher.getAttribute('src')).toMatch(/^https:\/\/acrobat.adobe.com\//); + }); + + it.each` + hostname + ${'stage--dc--adobecom.hlx.page'} + ${'main--dc--adobecom.hlx.page'} + ${'stage--dc--adobecom.hlx.live'} + ${'main--dc--adobecom.hlx.live'} + ${'www.stage.adobe.com'} + `('loads widget from stage env', async ({ hostname }) => { + let fetchUrl = ''; + window.fetch = jest.fn((url) => { + fetchUrl = url; + return Promise.resolve({ + status: 200, + text: () => + Promise.resolve( + fs.readFileSync(path.resolve(__dirname, './mocks/widget.html')) + ), + }); + }); + delete window.location; + window.location = new URL(`https://${hostname}`); + const block = document.querySelector('.dc-converter-widget-ootb'); + const widget = await init(block); + document.dispatchEvent(new Event('milo:deferred')); + const launcher = document.querySelector('#adobe_dc_sdk_launcher'); + expect(launcher.getAttribute('src')).toMatch(/^https:\/\/stage.acrobat.adobe.com\//); + }); + + it('loads widget failed from prod env', async () => { + window.fetch = jest.fn(() => + Promise.resolve({ + status: 404, + }) + ); + delete window.location; + window.location = new URL('https://www.adobe.com'); + const block = document.querySelector('.dc-converter-widget-ootb'); + const widget = await init(block); + expect(document.querySelector('#CID').children).toHaveLength(3); + }); + + it.each` + hostname + ${'stage--dc--adobecom.hlx.page'} + ${'main--dc--adobecom.hlx.page'} + ${'stage--dc--adobecom.hlx.live'} + ${'www.stage.adobe.com'} + `('redirects when signed in on stage', async ({ hostname }) => { + window.fetch = jest.fn((url) => + Promise.resolve({ + status: 200, + text: () => + Promise.resolve( + fs.readFileSync(path.resolve(__dirname, './mocks/widget.html')) + ), + }) + ); + window.adobeIMS = { + isSignedInUser: jest.fn(() => true) + }; + delete window.location; + window.location = new URL(`https://${hostname}`); + const block = document.querySelector('.dc-converter-widget-ootb'); + const widget = await init(block); + window.dispatchEvent(new CustomEvent('IMS:Ready')); + expect(window.location).toMatch(/^https:\/\/www.adobe.com\/go\/acrobat-/); + }); + + it.each` + hostname + ${'main--dc--adobecom.hlx.live'} + ${'www.adobe.com'} + `('redirects when signed in', async ({ hostname }) => { + window.fetch = jest.fn((url) => + Promise.resolve({ + status: 200, + text: () => + Promise.resolve( + fs.readFileSync(path.resolve(__dirname, './mocks/widget.html')) + ), + }) + ); + window.adobeIMS = { + isSignedInUser: jest.fn(() => true) + }; + delete window.location; + window.location = new URL(`https://${hostname}`); + const block = document.querySelector('.dc-converter-widget-ootb'); + const widget = await init(block); + window.dispatchEvent(new CustomEvent('IMS:Ready')); + // Issue with jest and window.location + //expect(window.location).toMatch(/https:\/\/www.adobe.com\/go\/testredirect/); + }); +}); diff --git a/test/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.test.js b/test/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.test.js new file mode 100644 index 00000000..1af654cb --- /dev/null +++ b/test/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb.test.js @@ -0,0 +1,62 @@ +import { readFile } from '@web/test-runner-commands'; +import { expect } from '@esm-bundle/chai'; +import sinon from 'sinon'; +import { waitForElement, delay } from '../../helpers/waitfor.js'; + +document.head.innerHTML = await readFile({ path: './mocks/head.html' }); +document.body.innerHTML = await readFile({ path: './mocks/body_cache.html' }); +const { default: init } = await import( + '../../../acrobat/blocks/dc-converter-widget-ootb/dc-converter-widget-ootb' +); + +describe('dc-converter-widget block', () => { + before(() => { + const block = document.body.querySelector('.dc-converter-widget-ootb'); + init(block); + }); + + afterEach(() => { + sinon.restore(); + }); + + it('handles DC_Hosted:Ready event', async() => { + window.dc_hosted = { + getUserLimits: async () => ({ + upload: { + can_upload: true + } + }), + }; + window.dispatchEvent(new CustomEvent('DC_Hosted:Ready')); + await delay(100); + expect(window.doccloudPersonalization).to.be.exist; + }); + + it('handles IMS:Ready event', async () => { + window.adobeIMS = { + isSignedInUser: () => false, + }; + window._satellite = { + track: sinon.stub(), + }; + window.bowser = { + getParser: () => ({ + getBrowserName: () => 'Chrome', + getBrowserVersion: () => '110', + }), + }; + const widget = await readFile({ path: './mocks/widget.html' }); + sinon.stub(window, 'fetch'); + var res = new window.Response(widget, { + status: 200 + }); + window.fetch.returns(Promise.resolve(res)); + window.dispatchEvent(new CustomEvent('IMS:Ready')); + await delay(1000); + expect(document.querySelector('#CID')).to.be.exist; + }); + + it('handles Bowser:Ready event', () => { + window.dispatchEvent(new CustomEvent('Bowser:Ready')); + }); +}); diff --git a/test/blocks/dc-converter-widget-ootb/mocks/body.html b/test/blocks/dc-converter-widget-ootb/mocks/body.html new file mode 100644 index 00000000..f52513ae --- /dev/null +++ b/test/blocks/dc-converter-widget-ootb/mocks/body.html @@ -0,0 +1,10 @@ +
+
+
+
pdf-to-ppt
+
+
+
https://www.adobe.com/go/testredirect
+
+
+
diff --git a/test/blocks/dc-converter-widget-ootb/mocks/body_cache.html b/test/blocks/dc-converter-widget-ootb/mocks/body_cache.html new file mode 100644 index 00000000..e6f62398 --- /dev/null +++ b/test/blocks/dc-converter-widget-ootb/mocks/body_cache.html @@ -0,0 +1,16 @@ +
+
+
+
pdf-to-ppt
+
+
+
https://www.adobe.com/go/testredirect
+
+
+
+
+
+
http://localhost:2000/test/blocks/dc-converter-widget-ootb/mocks/widget.html
+
+
+
diff --git a/test/blocks/dc-converter-widget-ootb/mocks/head.html b/test/blocks/dc-converter-widget-ootb/mocks/head.html new file mode 100644 index 00000000..c7297a2b --- /dev/null +++ b/test/blocks/dc-converter-widget-ootb/mocks/head.html @@ -0,0 +1,3 @@ + + + \ No newline at end of file diff --git a/test/blocks/dc-converter-widget-ootb/mocks/widget.html b/test/blocks/dc-converter-widget-ootb/mocks/widget.html new file mode 100644 index 00000000..c32ce9fb --- /dev/null +++ b/test/blocks/dc-converter-widget-ootb/mocks/widget.html @@ -0,0 +1,16 @@ + + + + + + + + +
+ + + \ No newline at end of file diff --git a/test/blocks/eventwrapper/eventwrapper.test.js b/test/blocks/eventwrapper/eventwrapper.test.js index a9509409..2eb16cb9 100644 --- a/test/blocks/eventwrapper/eventwrapper.test.js +++ b/test/blocks/eventwrapper/eventwrapper.test.js @@ -11,6 +11,7 @@ const { default: init } = await import( describe('eventwrapper block', () => { let browserName = 'Chrome'; + let chromeRuntimeSendMessage = false; before(() => { window.dc_hosted = { @@ -40,7 +41,7 @@ describe('eventwrapper block', () => { window.chrome = { runtime: { sendMessage: function (message, version, callback) { - callback(false); + callback((() => chromeRuntimeSendMessage)()); }, }, }; @@ -75,6 +76,39 @@ describe('eventwrapper block', () => { expect(window.modalDisplayed).to.be.true; }); + it('handles modalExist', async function () { + document.head.innerHTML = head; + document.body.innerHTML = body; + window.dc_hosted.listeners = []; + localStorage.removeItem('fricBrowExt'); + window.modalDisplayed = false; + chromeRuntimeSendMessage = true; + const blocks = document.body.querySelectorAll('.eventwrapper'); + blocks.forEach((x) => init(x)); + window.dispatchEvent(new CustomEvent('DC_Hosted:Ready')); + window.dc_hosted.dispatchEvent('conversion-complete', {}); + + window.modalDisplayed = false; + window.dc_hosted.dispatchEvent('preview-displayed', {}); + + // modalExist + const event = window._satellite.track.args[1][1].data._adobe_corpnew.digitalData.primaryEvent.eventInfo.eventName; + expect(event).to.eql('Get the extension-1|viewer-extension-exists|Chrome-extension'); + }); + + it('handles modalAlready', async function () { + document.head.innerHTML = head; + document.body.innerHTML = body; + localStorage.fricBrowExt = 'true'; + const blocks = document.body.querySelectorAll('.eventwrapper'); + blocks.forEach((x) => init(x)); + window.dispatchEvent(new CustomEvent('DC_Hosted:Ready')); + + // modalAlready + const event = window._satellite.track.args[1][1].data._adobe_corpnew.digitalData.primaryEvent.eventInfo.eventName; + expect(event).to.eql('Get the extension-1|already-closed-viewer-extension|Chrome-extension'); + }); + it('shows the ext modal on MS Edge when conversion complete and preview displayed', async function () { browserName = 'Microsoft Edge'; document.head.innerHTML = head; diff --git a/test/blocks/pricing-card/mocks/body_noinitialoption.html b/test/blocks/pricing-card/mocks/body_noinitialoption.html new file mode 100644 index 00000000..49675a8b --- /dev/null +++ b/test/blocks/pricing-card/mocks/body_noinitialoption.html @@ -0,0 +1,77 @@ +
+
+
+
+
title
+
+

Acrobat Pro2

+

For students & teachers

+
+
+
+
option1
+
Annual, paid monthly2
+
+
+
option2
+
Annual, prepaid2
+
+
+
option3
+
Monthly2
+
+
+
promotionText
+
Best value2
+
+
+
price1
+
US$3339.99/m
+
+
+
price2
+
US$439.99/m
+
+
+
price3
+
US$539.99/m
+
+
+
cta1
+
link133
+
+
+
cta2
+
link233
+
+
+
cta3
+
link333
+
+
+
disclaimer1
+
Equal to US$5339.99/mo. Cancel within 14 days for a full refund. + Windows and Mac.
+
+
+
disclaimer2
+
Equal to US$6339.99/mo. Cancel within 14 days for a full refund. + Windows and Mac.
+
+
+
disclaimer3
+
Equal to US$7339.99/mo. Cancel within 14 days for a full refund. + Windows and Mac.
+
+
+ +
+
\ No newline at end of file diff --git a/test/blocks/pricing-card/pricing-card.test.js b/test/blocks/pricing-card/pricing-card.test.js index d14e185d..5a8c702e 100644 --- a/test/blocks/pricing-card/pricing-card.test.js +++ b/test/blocks/pricing-card/pricing-card.test.js @@ -3,8 +3,8 @@ import { expect } from '@esm-bundle/chai'; import * as sinon from 'sinon'; import { waitForElement, delay } from '../../helpers/waitfor.js'; -let head = await readFile({ path: './mocks/head.html' }); -let body = await readFile({ path: './mocks/body.html' }); +const head = await readFile({ path: './mocks/head.html' }); + const { default: init } = await import( '../../../acrobat/blocks/pricing-card/pricing-card' ); @@ -12,10 +12,29 @@ const { default: init } = await import( describe('pricing-card block', () => { it('shoud creates a promotion block', async () => { document.head.innerHTML = head; - document.body.innerHTML = body; + document.body.innerHTML = await readFile({ path: './mocks/body.html' }); const block = await waitForElement('.pricing-card'); await init(block); const card = await waitForElement('.card-box'); expect(card).to.be.exist; + const buttons = [...document.querySelectorAll('input[type="radio"]')]; + expect(buttons[2].checked).to.be.true; + buttons[0].click(); + expect(buttons[0].checked).to.be.true; + expect(buttons[2].checked).to.be.false; }); + + it('shoud creates a promotion block, no initial option', async () => { + document.head.innerHTML = head; + document.body.innerHTML = await readFile({ path: './mocks/body_noinitialoption.html' }); + const block = await waitForElement('.pricing-card'); + await init(block); + const card = await waitForElement('.card-box'); + expect(card).to.be.exist; + const buttons = [...document.querySelectorAll('input[type="radio"]')]; + expect(buttons[0].checked).to.be.true; + buttons[1].click(); + expect(buttons[0].checked).to.be.false; + expect(buttons[1].checked).to.be.true; + }); }); diff --git a/test/blocks/promotion/mocks/body.html b/test/blocks/promotion/mocks/body.html deleted file mode 100644 index f4b4e456..00000000 --- a/test/blocks/promotion/mocks/body.html +++ /dev/null @@ -1,4 +0,0 @@ -
-
-
-
diff --git a/test/blocks/promotion/mocks/body_empty.html b/test/blocks/promotion/mocks/body_empty.html deleted file mode 100644 index 5612b362..00000000 --- a/test/blocks/promotion/mocks/body_empty.html +++ /dev/null @@ -1,4 +0,0 @@ -
-
-
-
diff --git a/test/blocks/promotion/mocks/fetch.html b/test/blocks/promotion/mocks/fetch.html deleted file mode 100644 index d3e17714..00000000 --- a/test/blocks/promotion/mocks/fetch.html +++ /dev/null @@ -1,20 +0,0 @@ -
-
-
-
-

Do more with Adobe Creative Cloud.

- -
-
-
-
\ No newline at end of file diff --git a/test/blocks/promotion/mocks/head.html b/test/blocks/promotion/mocks/head.html deleted file mode 100644 index f69e160d..00000000 --- a/test/blocks/promotion/mocks/head.html +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/test/blocks/promotion/promotion.test.js b/test/blocks/promotion/promotion.test.js deleted file mode 100644 index b1dd582c..00000000 --- a/test/blocks/promotion/promotion.test.js +++ /dev/null @@ -1,73 +0,0 @@ -import { readFile } from '@web/test-runner-commands'; -import { expect } from '@esm-bundle/chai'; -import * as sinon from 'sinon'; -import { waitForElement, delay } from '../../helpers/waitfor.js'; - -let meta = document.createElement('meta'); -meta.name = 'promotion'; -meta.content = 'ccx-acrobat-links1'; -document.getElementsByTagName('head')[0].appendChild(meta); -let head = await readFile({ path: './mocks/head.html' }); -let body = await readFile({ path: './mocks/body.html' }); -let bodyEmpty = await readFile({ path: './mocks/body_empty.html' }); -await import('../../../acrobat/scripts/scripts'); -const { default: init, promotionFromMetadata } = await import( - '../../../acrobat/blocks/promotion/promotion' -); - -describe('promotion block', () => { - beforeEach(() => { - document.head.innerHTML = head; - }); - - afterEach(() => { - sinon.restore(); - }); - - it('shoud creates a promotion block', async () => { - document.body.innerHTML = body; - const block = await waitForElement('.promotion'); - const fetchText = await readFile({ path: './mocks/fetch.html' }); - sinon.stub(window, 'fetch'); - var res = new window.Response(fetchText, { - status: 200 - }); - window.fetch.returns(Promise.resolve(res)); - await init(block); - const promotion = await waitForElement('.promotion'); - expect(promotion.textContent).to.contain('Do more with Adobe Creative Cloud.'); - }); - - it('has an empty promotion block after fetch empty', async () => { - document.body.innerHTML = body; - const block = await waitForElement('.promotion'); - sinon.stub(window, 'fetch'); - var res = new window.Response('', { - status: 200 - }); - window.fetch.returns(Promise.resolve(res)); - await init(block); - const promotion = await waitForElement('.promotion'); - expect(promotion.textContent).to.contain(''); - }); - - it('has an empty promotion block after fetch error', async () => { - document.body.innerHTML = body; - const block = await waitForElement('.promotion'); - sinon.stub(window, 'fetch'); - var res = new window.Response('File not found', { - status: 404 - }); - window.fetch.returns(Promise.resolve(res)); - await init(block); - const promotion = await waitForElement('.promotion'); - expect(promotion.textContent).to.contain(''); - }); - - it('creates a promotion block from metadata', async () => { - document.body.innerHTML = bodyEmpty; - await promotionFromMetadata('Abc'); - const promotion = await waitForElement('.promotion'); - expect(promotion.dataset.promotion).to.eql('abc'); - }); -}); diff --git a/test/e2e/frictionless/configs/acom_locales.yml b/test/e2e/frictionless/configs/acom_locales.yml new file mode 100644 index 00000000..13ba74e6 --- /dev/null +++ b/test/e2e/frictionless/configs/acom_locales.yml @@ -0,0 +1,884 @@ +- name: United States + locale: '' + region: United States + regionHeading: Choose your region + language: English + author: us/en + international: us + akamai: us + tier: 1 +- name: Brasil + locale: br + region: Brazil + regionHeading: Escolha sua região + language: Brazilian Portuguese + author: br/pt + international: br + akamai: br + tier: 3 +- name: Canada - English + locale: ca + region: Canada + regionHeading: Choose your region + language: English + author: ca/en + international: ca + akamai: ca + tier: 1 +- name: Canada - Français + locale: ca_fr + region: Canada + regionHeading: Choisissez votre région + language: French + author: ca/fr + international: ca_fr + akamai: ca + tier: 1 +- name: México + locale: mx + region: Mexico + regionHeading: Seleccionar región + language: Spanish + author: mx/es + international: mx + akamai: mx + tier: 3 +- name: Latinoamérica + locale: la + region: Latin America + regionHeading: Seleccionar región + language: Spanish + author: la/es + international: la + akamai: la + tier: 3 +- name: Africa - English + locale: africa + region: Africa + regionHeading: Choose your region + language: English + author: africa/en + international: africa + akamai: africa + tier: 4 +- name: South Africa + locale: za + region: Africa + regionHeading: Choose your region + language: English + author: za/en + international: za + akamai: za + tier: 4 +- name: België - Nederlands + locale: be_nl + region: Belgium + regionHeading: Kies je regio + language: Dutch + author: be/nl + international: be_nl + akamai: be + tier: 4 +- name: Belgique - Français + locale: be_fr + region: Belgium + regionHeading: Choisissez votre région + language: French + author: be/fr + international: be_fr + akamai: be + tier: 4 +- name: Belgium - English + locale: be_en + region: Belgium + regionHeading: Choose your region + language: English + author: be/en + international: be_en + akamai: be + tier: 4 +- name: Česká republika + locale: cz + region: Czech Republic + regionHeading: Zvolte oblast + language: Czech + author: cz/cs + international: cz + akamai: cz + tier: 4 +- name: Cyprus - English + locale: cy_en + region: Cyprus + regionHeading: Choose your region + language: English + author: cy/en + international: cy_en + akamai: cy + tier: 4 +- name: Danmark + locale: dk + region: Denmark + regionHeading: Vælg dit område + language: Danish + author: dk/da + international: dk + akamai: dk + tier: 2 +- name: Deutschland + locale: de + region: Germany + regionHeading: Region wählen + language: German + author: de/de + international: de + akamai: de + tier: 1 +- name: Estonia - English + locale: ee + region: Estonia + regionHeading: Choose your region + language: Estonian + author: ee/en + international: ee + akamai: ee + tier: 4 +- name: España + locale: es + region: Spain + regionHeading: Seleccionar región + language: Spanish + author: es/es + international: es + akamai: es + tier: 2 +- name: France + locale: fr + region: France + regionHeading: Choisissez votre région + language: French + author: fr/fr + international: fr + akamai: fr + tier: 1 +- name: Greece - English + locale: gr_en + region: Greece + regionHeading: Choose your region + language: English + author: gr/en + international: gr_en + akamai: gr + tier: 4 +- name: Greece - Greek + locale: gr_el + region: Greece + language: Greek + author: gr/el + international: gr_el + akamai: gr + tier: 4 +- name: Ireland + locale: ie + region: Ireland + regionHeading: Choose your region + language: English + author: ie/en + international: ie + akamai: ie + tier: 4 +- name: Israel - English + locale: il_en + region: Israel + regionHeading: Choose your region + language: English + author: il/en + international: il_en + akamai: il + tier: 4 +- name: Italia + locale: it + region: Italy + regionHeading: Scegli il paese + language: Italian + author: it/it + international: it + akamai: it + tier: 2 +- name: Latvia - English + locale: lv + region: Latvia + regionHeading: Choose your region + language: Latvian + author: lv/en + international: lv + akamai: lv + tier: 4 +- name: Lithuania - English + locale: lt + region: Lithuania + regionHeading: Choose your region + language: Lithuanian + author: lt/en + international: lt + akamai: lt + tier: 4 +- name: Luxembourg - Deutsch + locale: lu_de + region: Luxembourg + regionHeading: Region wählen + language: German + author: lu/de + international: lu_de + akamai: lu + tier: 4 +- name: Luxembourg - English + locale: lu_en + region: Luxembourg + regionHeading: Choose your region + language: English + author: lu/en + international: lu_en + akamai: lu + tier: 4 +- name: Luxembourg - Français + locale: lu_fr + region: Luxembourg + regionHeading: Choisissez votre région + language: French + author: lu/fr + international: lu_fr + akamai: lu + tier: 4 +- name: Magyarország + locale: hu + region: Hungary + regionHeading: Térségválasztás + language: Hungarian + author: hu/hu + international: hu + akamai: hu + tier: 4 +- name: Malta - English + locale: mt + region: Malta + regionHeading: Choose your region + language: English + author: mt/en + international: mt + akamai: mt + tier: 4 +- name: Middle East and North Africa - English + locale: mena_en + region: Middle East and North Africa + regionHeading: Choose your region + language: English + author: mena/en + international: mena_en + akamai: mena + tier: 4 +- name: Middle East and North Africa - Arabic + locale: mena_ar + region: Middle East and North Africa + regionHeading: Choose your region + language: Arabic + author: mena/ar + international: mena_ar + akamai: mena + tier: 4 +- name: Nederland + locale: nl + region: Netherlands + regionHeading: Kies je regio + language: Dutch + author: nl/nl + international: nl + akamai: nl + tier: 2 +- name: Norge + locale: no + region: Norway + regionHeading: Velg ditt område + language: Norwegian + author: no/no + international: 'no' + akamai: 'no' + tier: 2 +- name: Österreich + locale: at + region: Austria + regionHeading: Region wählen + language: German + author: at/de + international: at + akamai: at + tier: 4 +- name: Polska + locale: pl + region: Poland + regionHeading: Wybierz region + language: Polish + author: pl/pl + international: pl + akamai: pl + tier: 4 +- name: Portugal + locale: pt + region: Portugal + regionHeading: Escolha sua região + language: Portuguese + author: pt/pt + international: pt + akamai: pt + tier: 4 +- name: Romania - English + locale: ro + region: Romania + regionHeading: Selectați regiunea + language: Romanian + author: ro/ro + international: ro + akamai: ro + tier: 4 +- name: Schweiz + locale: ch_de + region: Switzerland + regionHeading: Region wählen + language: German + author: ch/de + international: ch_de + akamai: ch + tier: 4 +- name: Slovenia - English + locale: si + region: Slovenia + regionHeading: Izberite regijo + language: Slovenian + author: si/si + international: si + akamai: si + tier: 4 +- name: Slovakia - English + locale: sk + region: Slovakia + regionHeading: Izberite regijo + language: Slovakian + author: sk/sk + international: sk + akamai: sk + tier: 4 +- name: Suisse + locale: ch_fr + region: Switzerland + regionHeading: Choisissez votre région + language: French + author: ch/fr + international: ch_fr + akamai: ch + tier: 4 +- name: Suomi + locale: fi + region: Finland + regionHeading: Valitse oma alueesi + language: Finnish + author: fi/fi + international: fi + akamai: fi + tier: 2 +- name: Sverige + locale: se + region: Sweden + regionHeading: Ange region + language: Swedish + author: se/sv + international: se + akamai: se + tier: 2 +- name: Svizzera + locale: ch_it + region: Switzerland + regionHeading: Scegli il paese + language: Italian + author: ch/it + international: ch_it + akamai: ch + tier: 4 +- name: Türkiye + locale: tr + region: Turkey + regionHeading: Bölgenizi seçin + language: Turkish + author: tr/tr + international: tr + akamai: tr + tier: 4 +- name: United Kingdom + locale: uk + region: United Kingdom + regionHeading: Choose your region + language: English + author: uk/en + international: uk + akamai: uk + tier: 1 +- name: Bulgaria - English + locale: bg + region: Bulgaria + regionHeading: Choose your region + language: Bulgarian + author: bg/en + international: bg + akamai: bg + tier: 4 +- name: Россия + locale: ru + region: Russia + regionHeading: Выбрать регион + language: Russian + author: ru/ru + international: ru + akamai: ru + tier: 4 +- name: Ukraine - English + locale: ua + region: Ukraine + regionHeading: Оберіть свій регіон + language: Ukranian + author: ua/ua + international: ua + akamai: ua + tier: 4 +- name: Australia + locale: au + region: Australia + regionHeading: Choose your region + language: English + author: au/en + international: au + akamai: au + tier: 1 +- name: Hong Kong S.A.R. of China + locale: hk_en + region: Hong Kong + regionHeading: Choose your region + language: English + author: hk/en + international: hk_en + akamai: hk + tier: 3 +- name: India - English + locale: in + region: India + regionHeading: Choose your region + language: English + author: in/en + international: in + akamai: in + tier: 3 +- name: भारत + locale: in_hi + region: India + regionHeading: अपना क्षेत्र चुनें + language: Hindi + author: in/hi + international: in_hi + akamai: in + tier: 3 +- name: New Zealand + locale: nz + region: New Zealand + regionHeading: Choose your region + language: English + author: nz/en + international: nz + akamai: nz + tier: 1 +# - name: Southeast Asia (Includes Indonesia, Malaysia, Philippines, Singapore, Thailand, and Vietnam) - English +# locale: sea +# region: South East Asia +# regionHeading: Choose your region +# language: English +# author: sea/en +# international: sea +# akamai: sea +# tier: 3 +- name: 中國香港特別行政區 + locale: hk_zh + region: Hong Kong + regionHeading: 選擇您的地區 + language: Chinese Traditional + author: hk/zh-Hant + international: hk + akamai: hk + tier: 3 +- name: 中国 + locale: cn + region: China + regionHeading: 选择地区 + language: Chinese Simplified + author: cn/zh-Hans + international: cn + akamai: cn + tier: 3 +- name: 台灣地區 + locale: tw + region: Taiwan area + regionHeading: 選擇您的地區 + language: Chinese Traditional + author: tw/zh-Hant + international: tw + akamai: tw + tier: 3 +- name: 日本 + locale: jp + region: Japan + regionHeading: 地域を選択してください + language: Japanese + author: jp/ja + international: jp + akamai: jp + tier: 1 +- name: 한국 + locale: kr + region: Korea + regionHeading: 지역 선택 + language: Korean + author: kr/ko + international: kr + akamai: kr + tier: 3 +- name: United Arab Emirates - English + locale: ae_en + region: United Arab Emirates + regionHeading: Change region + language: English + browser: en_ae + akamai: ae + author: ae/en + international: ae_en + tier: 4 +- name: United Arab Emirates - Arabic + locale: ae_ar + region: United Arab Emirates + language: Arabic + browser: ar_ae + akamai: ae + author: ae/ar + international: ae_ar + tier: 4 +- name: Saudi Arabia - English + locale: sa_en + region: Saudi Arabia + regionHeading: Change region + language: English + browser: en_sa + akamai: sa + author: sa/en + international: sa_en + tier: 4 +- name: Saudi Arabia - Arabic + locale: sa_ar + region: Saudi Arabia + language: Arabic + akamai: sa + author: sa/ar + international: sa_ar + tier: 4 +- name: Thailand - English + locale: th_en + region: Thailand + regionHeading: Change region + language: English + browser: en_th + akamai: th + author: th/en + international: th_en + tier: 3 +- name: ประเทศไทย + locale: th_th + region: Thailand + regionHeading: เลือกภูมิภาคของคุณ + language: Thai + browser: th_th + akamai: th + author: th/th + international: th_th + tier: 3 +- name: Singapore + locale: sg + region: Singapore + regionHeading: Change region + language: English + browser: en_sg + akamai: sg + author: sg/en + international: sg + tier: 3 +- name: Chile + locale: cl + region: Chile + regionHeading: Cambiar región + language: Spanish + browser: cl_es + akamai: cl + author: cl/es + international: cl + tier: 3 +- name: Colombia + locale: co + region: Colombia + regionHeading: Cambiar región + language: Spanish + browser: co_es + akamai: co + author: co/es + international: co + tier: 3 +- name: Argentina + locale: ar + region: Argentina + regionHeading: Cambiar región + language: Spanish + browser: ar_es + akamai: ar + author: ar/es + international: ar + tier: 3 +- name: Bahrain + locale: bh + akamai: bh + author: bh/en + tier: 4 +- name: Bolivia + locale: bo + akamai: bo + author: bo/es + tier: 4 +- name: Costa Rica + locale: cr + akamai: cr + author: cr/es + tier: 3 +- name: Dominican Republic + locale: do + akamai: do + author: do/es + tier: 4 +- name: Puerto Rico + locale: pr + akamai: pr + author: pr/es + tier: 4 +- name: Algeria + locale: dz + akamai: dz + author: dz/en + tier: 4 +- name: Ecuador + locale: ec + akamai: ec + author: ec/es + tier: 3 +- name: Peru + locale: pe + region: Peru + language: Spanish + browser: pe_es + akamai: pe + author: pe/es + international: pe + tier: 3 +- name: Egypt - English + locale: eg_en + akamai: eg + author: eg/en + tier: 4 +- name: Egypt - Arabic + locale: eg_ar + akamai: eg + author: eg/ar + tier: 4 +- name: Guatemala + locale: gt + akamai: gt + author: gt/es + tier: 3 +- name: Croatia + locale: hr + akamai: hr + author: hr/hr + tier: 4 +- name: Croatia + locale: hr + akamai: hr + author: hr/en +- name: Indonesia - English + region: Indonesia + locale: id_en + akamai: id + author: id/en + tier: 3 +- name: Indonesia + region: Indonesia + locale: id_id + akamai: id + author: id/id + tier: 3 +- name: Philippines - English + region: Philippines + locale: ph_en + akamai: ph + author: ph/en + tier: 3 +- name: Pilipinas + region: Philippines + locale: ph_fil + akamai: ph + author: ph/fil + tier: 3 +- name: Malaysia - English + region: Malaysia + locale: my_en + akamai: my + author: my/en + tier: 3 +- name: Malaysia + region: Malaysia + locale: my_ms + akamai: my + author: my/ms + tier: 3 +- name: Jordan + locale: jo + akamai: jo + author: jo/en + tier: 4 +- name: Kenya + locale: ke + language: English + browser: ke_en + akamai: ke + international: ke + author: ke/en + tier: 4 +- name: Kuwait - English + locale: kw_en + akamai: kw + author: kw/en + tier: 4 +- name: Kuwait - Arabic + locale: kw_ar + akamai: kw + author: kw/ar + tier: 4 +- name: Libya + locale: lb + akamai: lb + author: lb/en + tier: 4 +- name: Sri Lanka + locale: lk + akamai: lk + author: lk/en + tier: 4 +- name: Morocco + locale: ma + akamai: ma + author: ma/en + tier: 4 +- name: Macao - English + locale: mo + akamai: mo + author: mo/en + tier: 4 +- name: Mauritius + locale: mu + akamai: mu + author: mu/en + tier: 4 +- name: Nigeria + locale: ng + regionHeading: Change region + language: English + browser: ng_en + akamai: ng + author: ng/en + international: ng + tier: 4 +- name: Oman + locale: om + akamai: om + author: om/en + tier: 4 +- name: Panama + locale: pa + akamai: pa + author: pa/es + tier: 4 +- name: Paraguay + locale: py + akamai: py + author: py/es + tier: 4 +- name: Qatar - English + locale: qa_en + akamai: qa + author: qa/en + tier: 4 +- name: Qatar - Arabic + locale: qa_ar + akamai: qa + author: qa/ar + tier: 4 +- name: El Salvador + locale: sv + akamai: sv + author: sv/es + tier: 4 +- name: Trinidad and Tobago + locale: tt + regionHeading: Change region + language: English + browser: tt_en + akamai: tt + international: tt + author: tt/en + tier: 4 +- name: Tunisia + locale: tn + akamai: tn + author: tn/en + tier: 4 +- name: Uruguay + locale: uy + akamai: uy + author: uy/es + tier: 4 +- name: Venezuela + locale: ve + akamai: ve + author: ve/es + tier: 3 +- name: Vietnam - English + region: Vietnam + locale: vn_en + akamai: vn + author: vn/en + tier: 3 +- name: Việt Nam + region: Vietnam + locale: vn_vi + akamai: vn + author: vn/vi + tier: 3 +- name: Spain - Basque + region: Spain + locale: es_eu + akamai: es + author: es/eu + tier: 2 +- name: Spain - Catalan + region: Spain + locale: es_ca + akamai: es + author: es/ca + tier: 2 diff --git a/test/e2e/frictionless/configs/locales.yml b/test/e2e/frictionless/configs/locales.yml new file mode 100644 index 00000000..362b660a --- /dev/null +++ b/test/e2e/frictionless/configs/locales.yml @@ -0,0 +1,185 @@ +# Americas +ar: + ietf: es-AR +br: + ietf: pt-BR +ca: + ietf: en-CA +ca_fr: + ietf: fr-CA +cl: + ietf: es-CL +co: + ietf: es-CO +cr: + ietf: es-CR +ec: + ietf: es-EC +gt: + ietf: es-GT +la: + ietf: es-LA +mx: + ietf: es-MX +pe: + ietf: es-PE +pr: + ietf: es-PR +"": + ietf: en-US +# EMEA +africa: + ietf: en +be_fr: + ietf: fr-BE +be_en: + ietf: en-BE +be_nl: + ietf: nl-BE +cy_en: + ietf: en-CY +dk: + ietf: da-DK +de: + ietf: de-DE +ee: + ietf: et-EE +es: + ietf: es-ES +fr: + ietf: fr-FR +gr_el: + ietf: el-GR +gr_en: + ietf: en-GR +ie: + ietf: en-GB +il_en: + ietf: en-IL +it: + ietf: it-IT +lv: + ietf: lv-LV +lt: + ietf: lt-LT +lu_de: + ietf: de-LU +lu_en: + ietf: en-LU +lu_fr: + ietf: fr-LU +hu: + ietf: hu-HU +mt: + ietf: en-MT +mena_en: + ietf: en +ng: + ietf: en-NG +nl: + ietf: nl-NL +no: + ietf: no-NO +pl: + ietf: pl-PL +pt: + ietf: pt-PT +ro: + ietf: ro-RO +sa_en: + ietf: en +ch_de: + ietf: de-CH +si: + ietf: sl-SI +sk: + ietf: sk-SK +ch_fr: + ietf: fr-CH +fi: + ietf: fi-FI +se: + ietf: sv-SE +ch_it: + ietf: it-CH +tr: + ietf: tr-TR +ae_en: + ietf: en +uk: + ietf: en-GB +at: + ietf: de-AT +cz: + ietf: cs-CZ +bg: + ietf: bg-BG +ru: + ietf: ru-RU +ua: + ietf: uk-UA +# il_he: +# ietf: he +ae_ar: + ietf: ar-AE +mena_ar: + ietf: ar +sa_ar: + ietf: ar-SA +eg_ar: + ietf: ar-EG +eg_en: + ietf: en-EG +kw_ar: + ietf: ar-KW +kw_en: + ietf: en-KW +qa_ar: + ietf: ar-QA +qa_en: + ietf: en-QA +za: + ietf: en-ZA +# Asia Pacific +au: + ietf: en-AU +hk_en: + ietf: en-HK +in: + ietf: en-GB +id_id: + ietf: id +id_en: + ietf: en +my_ms: + ietf: ms +my_en: + ietf: en-GB +nz: + ietf: en-GB +ph_en: + ietf: en +ph_fil: + ietf: fil-PH +sg: + ietf: en-SG +th_en: + ietf: en +in_hi: + ietf: hi +th_th: + ietf: th +vn_en: + ietf: en-VN +vn_vi: + ietf: vi-VN +# cn: +# ietf: zh-CN +hk_zh: + ietf: zh-HK +tw: + ietf: zh-TW +jp: + ietf: ja-JP +kr: + ietf: ko-KR diff --git a/test/e2e/frictionless/configs/locales_t1.yml b/test/e2e/frictionless/configs/locales_t1.yml new file mode 100644 index 00000000..ccbf9687 --- /dev/null +++ b/test/e2e/frictionless/configs/locales_t1.yml @@ -0,0 +1,10 @@ +"": + ietf: en-US +de: + ietf: de-DE +fr: + ietf: fr-FR +jp: + ietf: ja-JP +uk: + ietf: en-GB \ No newline at end of file diff --git a/test/e2e/frictionless/configs/locales_t2.yml b/test/e2e/frictionless/configs/locales_t2.yml new file mode 100644 index 00000000..b55867db --- /dev/null +++ b/test/e2e/frictionless/configs/locales_t2.yml @@ -0,0 +1,22 @@ +au: + ietf: en-AU +ca: + ietf: en-CA +ca_fr: + ietf: fr-CA +dk: + ietf: da-DK +es: + ietf: es-ES +fi: + ietf: fi-FI +it: + ietf: it-IT +nl: + ietf: nl-NL +no: + ietf: no-NO +nz: + ietf: en-GB +se: + ietf: sv-SE \ No newline at end of file diff --git a/test/e2e/frictionless/configs/locales_t3.yml b/test/e2e/frictionless/configs/locales_t3.yml new file mode 100644 index 00000000..4d8b95fc --- /dev/null +++ b/test/e2e/frictionless/configs/locales_t3.yml @@ -0,0 +1,58 @@ +africa: + ietf: en +ar: + ietf: es-AR +br: + ietf: pt-BR +cl: + ietf: es-CL +co: + ietf: es-CO +cr: + ietf: es-CR +gt: + ietf: es-GT +hk_en: + ietf: en-HK +hk_zh: + ietf: zh-HK +id_en: + ietf: en-ID +id_id: + ietf: id-ID +in: + ietf: en-GB +in_hi: + ietf: hi-IN +kr: + ietf: ko-KR +la: + ietf: es-LA +mx: + ietf: es-MX +my_en: + ietf: en-GB +my_ms: + ietf: ms-MY +ng: + ietf: en-NG +pe: + ietf: es-PE +ph_en: + ietf: en-PH +ph_fil: + ietf: fil-PH +sg: + ietf: en-SG +th_en: + ietf: en-TH +th_th: + ietf: th-TH +tw: + ietf: zh-TW +vn_en: + ietf: en-VN +vn_vi: + ietf: vi-VN +za: + ietf: en-ZA \ No newline at end of file diff --git a/test/e2e/frictionless/configs/locales_t4.yml b/test/e2e/frictionless/configs/locales_t4.yml new file mode 100644 index 00000000..eb6d3e81 --- /dev/null +++ b/test/e2e/frictionless/configs/locales_t4.yml @@ -0,0 +1,88 @@ +ae_ar: + ietf: ar-AE +ae_en: + ietf: en +at: + ietf: de-AT +be_en: + ietf: en-BE +be_fr: + ietf: fr-BE +be_nl: + ietf: nl-BE +bg: + ietf: bg-BG +ch_de: + ietf: de-CH +ch_fr: + ietf: fr-CH +ch_it: + ietf: it-CH +cy_en: + ietf: en-CY +cz: + ietf: cs-CZ +ec: + ietf: es-EC +ee: + ietf: et-EE +eg_ar: + ietf: ar-EG +eg_en: + ietf: en-EG +gr_el: + ietf: el-GR +gr_en: + ietf: en-GR +hu: + ietf: hu-HU +ie: + ietf: en-GB +il_en: + ietf: en-IL +kw_ar: + ietf: ar-KW +kw_en: + ietf: en-KW +lt: + ietf: lt-LT +lu_de: + ietf: de-LU +lu_en: + ietf: en-LU +lu_fr: + ietf: fr-LU +lv: + ietf: lv-LV +mena_ar: + ietf: ar +mena_en: + ietf: en +mt: + ietf: en-MT +pl: + ietf: pl-PL +pr: + ietf: es-PR +pt: + ietf: pt-PT +qa_ar: + ietf: ar-QA +qa_en: + ietf: en-QA +ro: + ietf: ro-RO +ru: + ietf: ru-RU +sa_ar: + ietf: ar-SA +sa_en: + ietf: en +si: + ietf: sl-SI +sk: + ietf: sk-SK +tr: + ietf: tr-TR +ua: + ietf: uk-UA \ No newline at end of file diff --git a/test/e2e/frictionless/configs/locales_us.yml b/test/e2e/frictionless/configs/locales_us.yml new file mode 100644 index 00000000..5caf889b --- /dev/null +++ b/test/e2e/frictionless/configs/locales_us.yml @@ -0,0 +1,2 @@ +"": + ietf: en-US diff --git a/test/e2e/frictionless/configs/pages.yml b/test/e2e/frictionless/configs/pages.yml new file mode 100644 index 00000000..50a5220a --- /dev/null +++ b/test/e2e/frictionless/configs/pages.yml @@ -0,0 +1,35 @@ +add-pages-to-pdf: + verb: insert-pdf +compress-pdf: +convert-pdf: + verb: createpdf +crop-pdf: + verb: crop-pages +delete-pdf-pages: + verb: delete-pages +excel-to-pdf: +extract-pdf-pages: + verb: extract-pages +jpg-to-pdf: +merge-pdf: + verb: combine-pdf +password-protect-pdf: + verb: protect-pdf +pdf-editor: + verb: add-comment +pdf-to-excel: +pdf-to-jpg: + verb: pdf-to-image +pdf-to-ppt: +pdf-to-word: +png-to-pdf: +ppt-to-pdf: +rearrange-pdf: + verb: reorder-pages +request-signature: + verb: sendforsignature +rotate-pdf: + verb: rotate-pages +sign-pdf: + verb: fillsign +split-pdf: diff --git a/test/e2e/frictionless/configs/pages_t1.yml b/test/e2e/frictionless/configs/pages_t1.yml new file mode 100644 index 00000000..d0c61653 --- /dev/null +++ b/test/e2e/frictionless/configs/pages_t1.yml @@ -0,0 +1,19 @@ +add-pages-to-pdf: + verb: insert-pdf +crop-pdf: + verb: crop-pages +delete-pdf-pages: + verb: delete-pages +extract-pdf-pages: + verb: extract-pages +pdf-editor: + verb: add-comment +rearrange-pdf: + verb: reorder-pages +request-signature: + verb: sendforsignature +rotate-pdf: + verb: rotate-pages +sign-pdf: + verb: fillsign +split-pdf: \ No newline at end of file diff --git a/test/e2e/frictionless/configs/pages_t2.yml b/test/e2e/frictionless/configs/pages_t2.yml new file mode 100644 index 00000000..0c75bad2 --- /dev/null +++ b/test/e2e/frictionless/configs/pages_t2.yml @@ -0,0 +1,16 @@ +compress-pdf: +convert-pdf: + verb: createpdf +excel-to-pdf: +jpg-to-pdf: +merge-pdf: + verb: combine-pdf +password-protect-pdf: + verb: protect-pdf +pdf-to-excel: +pdf-to-jpg: + verb: pdf-to-image +pdf-to-ppt: +pdf-to-word: +png-to-pdf: +ppt-to-pdf: \ No newline at end of file diff --git a/test/e2e/frictionless/configs/verbs.yml b/test/e2e/frictionless/configs/verbs.yml new file mode 100644 index 00000000..0709ee74 --- /dev/null +++ b/test/e2e/frictionless/configs/verbs.yml @@ -0,0 +1,22 @@ +ppt-to-pdf: +rotate-pdf: +extract-pdf-pages: +rearrange-pdf: +add-pages-to-pdf: +split-pdf: +jpg-to-pdf: +pdf-to-jpg: +pdf-to-word: +merge-pdf: +compress-pdf: +word-to-pdf: +convert-pdf: +sign-pdf: +excel-to-pdf: +pdf-to-ppt: +crop-pdf: +delete-pdf-pages: +password-protect-pdf: +request-signature: +pdf-to-excel: +pdf-editor: \ No newline at end of file diff --git a/test/e2e/frictionless/features/demo.feature b/test/e2e/frictionless/features/demo.feature new file mode 100644 index 00000000..ada679f6 --- /dev/null +++ b/test/e2e/frictionless/features/demo.feature @@ -0,0 +1,14 @@ +Feature: Platform-UI Automation Demo + + @id-1 + Scenario: Convert PDF to PowerPoint + Given I go to the pdf-to-ppt page + Then I upload the PDF "test-files/test.pdf" + Then I download the converted file + + @id-2 + Scenario: Verify Adobe App Launcher + Given I go to the pdf-to-ppt page + Then I should not see the app launcher + When I sign in AdobeID + Then I should see "Convert PDF to PowerPoint" in the page content \ No newline at end of file diff --git a/test/e2e/frictionless/features/regression/analytics.feature b/test/e2e/frictionless/features/regression/analytics.feature new file mode 100644 index 00000000..a402e48e --- /dev/null +++ b/test/e2e/frictionless/features/regression/analytics.feature @@ -0,0 +1,21 @@ +Feature: Analytics - Frictionless Pages + + Background: + Given I have a new browser context + + @MWPW-130640 @regression-analytics + Scenario Outline: Analytics - Frictionless page load and download + Given I go to the page + Then I load expected analytics data from wiki page "2871483205" with replacements "" + Then I upload the file "" + Then I download the converted file + Then I wait for 3 seconds + And I should see analytics data posted within all logs matched with "Page load" + And I should see analytics data posted within all logs matched with "Download" + + Examples: + | Verb | Replacements | File | + | pdf-to-ppt | verb-id=verb-pdf-to-ppt | test-files/test.pdf | + | word-to-pdf | verb-id=verb-word-to-pdf | test-files/test.docx | + | excel-to-pdf | verb-id=verb-excel-to-pdf | test-files/test.xlsx | + | ppt-to-pdf | verb-id=verb-ppt-to-pdf | test-files/test.pptx | \ No newline at end of file diff --git a/test/e2e/frictionless/features/regression/converter.feature b/test/e2e/frictionless/features/regression/converter.feature new file mode 100644 index 00000000..19506fe2 --- /dev/null +++ b/test/e2e/frictionless/features/regression/converter.feature @@ -0,0 +1,85 @@ +Feature: Frictionless Converter Block + + Background: + Given I have a new browser context + + @MWPW-127201 @regression-converter + Scenario Outline: L1 Verbs - Upload and sign-in + Given I go to the page + Then I upload the file "" + Then I wait for the conversion + Then I continue with AdobeID + Then I wait for 5 seconds + Then I should see the address bar contains ".services.adobe.com" + + Examples: + | Verb | File | + | sign-pdf | test-files/test.pdf | + | request-signature | test-files/test.pdf | + | crop-pdf | test-files/test.pdf | + | delete-pdf-pages | test-files/test2.pdf | + # | rotate-pdf | test-files/test.pdf | + | rearrange-pdf | test-files/test.pdf | + | split-pdf | test-files/test2.pdf | + | add-pages-to-pdf | test-files/test.pdf | + | extract-pdf-pages | test-files/test2.pdf | + | pdf-editor | test-files/test.pdf | + + @MWPW-124781 @regression-converter + Scenario Outline: L2 Verbs - Upload and download + Given I go to the page + Then I upload the file "" + Then I download the converted file + + Examples: + | Verb | File | + | pdf-to-ppt | test-files/test.pdf | + | pdf-to-word | test-files/test.pdf | + | pdf-to-excel | test-files/test.pdf | + | convert-pdf | test-files/test.jpg | + | ppt-to-pdf | test-files/test.pptx | + | jpg-to-pdf | test-files/test.jpg | + | word-to-pdf | test-files/test.docx | + | excel-to-pdf | test-files/test.xlsx | + + @MWPW-124781 @regression-converter + Scenario Outline: L2 Verbs - Upload and download + Given I go to the page + Then I upload the file "" + Then I choose "JPG (*.jpg, *.jpeg)" as the output format + Then I download the converted file + + Examples: + | Verb | File | + | pdf-to-jpg | test-files/test.pdf | + + @MWPW-127201 @regression-converter + Scenario Outline: L2 Verbs - Upload and download + Given I go to the page + Then I upload the files "" + Then I merge the uploaded files + Then I download the converted file + + Examples: + | Verb | Files | + | merge-pdf | test-files/test.pdf,test-files/test2.pdf | + + @MWPW-129135 @regression-converter-headed-skip + Scenario Outline: L1 Verbs - Upload and sign-in with Google YOLO + Given I go to "https://www.google.com" + Then I click the element "text='Sign in'" + Then I wait for 2 seconds + Then I login to Google + + When I go to the page + Then I upload the file "" + Then I wait for the conversion + Then I should see the Google credential picker + Then I wait for 2 seconds + Then I click the Continue button inside the Google iFrame + Then I should see the file in DC Web + Then I delete the file in DC Web + + Examples: + | Verb | File | + | sign-pdf | test-files/test.pdf | \ No newline at end of file diff --git a/test/e2e/frictionless/features/regression/eventwrapper.feature b/test/e2e/frictionless/features/regression/eventwrapper.feature new file mode 100644 index 00000000..5206245a --- /dev/null +++ b/test/e2e/frictionless/features/regression/eventwrapper.feature @@ -0,0 +1,53 @@ +Feature: Frictionless Event Wrapper Block + + Background: + Given I have a new browser context + + @MWPW-127202 @regression-eventwrapper + Scenario Outline: L2 Verbs - Personalization events + Given I go to the page + Then I should see the default how-to + Then I upload the file "" + Then I download the converted file + + When I go to the page + Then I should see the 2nd conversion how-to + Then I upload the file "" + Then I wait for the conversion + + When I go to the page + Then I should see upsell + Then I should see the 2nd conversion how-to + + Examples: + | Verb | File | + | pdf-to-ppt | test-files/test.pdf | + # | pdf-to-word | test-files/test.pdf | + | pdf-to-excel | test-files/test.pdf | + | convert-pdf | test-files/test.docx | + | ppt-to-pdf | test-files/test.pptx | + | jpg-to-pdf | test-files/test.jpg | + | word-to-pdf | test-files/test.docx | + | excel-to-pdf | test-files/test.xlsx | + + @MWPW-127202 @regression-eventwrapper + Scenario Outline: L2 Verbs - Personalization events + Given I go to the page + Then I should see the default how-to + Then I upload the file "" + Then I choose "JPG (*.jpg, *.jpeg)" as the output format + Then I download the converted file + + When I go to the page + Then I should see the 2nd conversion how-to + Then I upload the file "" + Then I choose "JPG (*.jpg, *.jpeg)" as the output format + Then I wait for the conversion + + When I go to the page + Then I should see upsell + Then I should see the 2nd conversion how-to + + Examples: + | Verb | File | + | pdf-to-jpg | test-files/test.pdf | \ No newline at end of file diff --git a/test/e2e/frictionless/features/regression/extension.feature b/test/e2e/frictionless/features/regression/extension.feature new file mode 100644 index 00000000..d408d0f5 --- /dev/null +++ b/test/e2e/frictionless/features/regression/extension.feature @@ -0,0 +1,82 @@ +Feature: Frictionless Browser Extension Modal + + @MWPW-130086 @regression-ext-installed + Scenario Outline: Acrobat extension is already installed + Given I go to the page + Then I resize the browser window to 1366x768 + Then I upload the file "" + Then I wait for the conversion + Then I should not see a modal promoting the browser extension + + When I go to the page + Then I upload the file "" + Then I wait for the conversion + Then I should not see a modal promoting the browser extension + + When I go to the page + Then I should see upsell + Then I should not see a modal promoting the browser extension + + Examples: + | Verb | File | + | pdf-to-ppt | test-files/test.pdf | + + @MWPW-130086 @regression-ext-headed + Scenario Outline: Display the modal if Acrobat extension is not already installed + Given I have a new browser context + Given I go to the page + Then I resize the browser window to 1366x768 + Then I upload the file "" + Then I wait for the conversion + Then I should see a modal promoting the browser extension + + When I go to the page + Then I upload the file "" + Then I wait for the conversion + Then I should see a modal promoting the browser extension + + When I go to the page + Then I should see upsell + Then I should not see a modal promoting the browser extension + + Examples: + | Verb | File | + | excel-to-pdf | test-files/test.xlsx | + + @MWPW-130086 @regression-ext-headed + Scenario Outline: User dismisses the Acrobat extension modal + Given I have a new browser context + Given I go to the page + Then I resize the browser window to 1366x768 + Then I upload the file "" + Then I wait for the conversion + Then I should see a modal promoting the browser extension + Then I dismiss the extension modal + + When I go to the page + Then I upload the file "" + Then I wait for the conversion + Then I should not see a modal promoting the browser extension + + Examples: + | Verb | File | + | sign-pdf | test-files/test.pdf | + + @MWPW-130086 @regression-ext-headed + Scenario Outline: Mobile and tablets should not display the modal + Given I have a new browser context + Given I go to the page + Then I resize the browser window to 768x1024 + Then I upload the file "" + Then I wait for the conversion + Then I should not see a modal promoting the browser extension + + When I go to the page + Then I resize the browser window to 390x844 + Then I upload the file "" + Then I wait for the conversion + Then I should not see a modal promoting the browser extension + + Examples: + | Verb | File | + | sign-pdf | test-files/test.pdf | \ No newline at end of file diff --git a/test/e2e/frictionless/features/regression/review.feature b/test/e2e/frictionless/features/regression/review.feature new file mode 100644 index 00000000..26162ed3 --- /dev/null +++ b/test/e2e/frictionless/features/regression/review.feature @@ -0,0 +1,17 @@ +Feature: Frictionless Review Block + + Background: + Given I have a new browser context + + @MWPW-127204 @regression-review + Scenario Outline: Review rating and stats + Given I go to the page + Then I should see the review stats + When I submit review feedback + Then I should see the review submit response + + Examples: + | Verb | + | pdf-to-ppt | + | convert-pdf | + | pdf-editor | \ No newline at end of file diff --git a/test/e2e/frictionless/features/smoke/analytics.feature b/test/e2e/frictionless/features/smoke/analytics.feature new file mode 100644 index 00000000..cba51877 --- /dev/null +++ b/test/e2e/frictionless/features/smoke/analytics.feature @@ -0,0 +1,17 @@ +Feature: Analytics - Frictionless Pages + + Background: + Given I have a new browser context + + @MWPW-130083 @smoke-analytics + Scenario Outline: Analytics - Frictionless page load + Given I go to the page + Then I load expected analytics data from wiki page "2871483205" with replacements "" + Then I upload the file "test-files/test.pdf" + Then I download the converted file + Then I wait for 3 seconds + And I should see analytics data posted within all logs matched with "Page load" + + Examples: + | Verb | Replacements | + | pdf-to-ppt | verb-id=verb-pdf-to-ppt | \ No newline at end of file diff --git a/test/e2e/frictionless/features/smoke/converter.feature b/test/e2e/frictionless/features/smoke/converter.feature new file mode 100644 index 00000000..4514eff7 --- /dev/null +++ b/test/e2e/frictionless/features/smoke/converter.feature @@ -0,0 +1,27 @@ +Feature: Frictionless Converter Block + + Background: + Given I have a new browser context + + @MWPW-130446 @smoke-converter + Scenario Outline: L1 Verb - Upload and sign-in + Given I go to the page + Then I upload the file "" + Then I wait for the conversion + Then I continue with AdobeID + Then I wait for 5 seconds + Then I should see the address bar contains ".services.adobe.com" + + Examples: + | Verb | File | + | sign-pdf | test-files/test.pdf | + + @MWPW-130447 @smoke-converter + Scenario Outline: L2 Verb - Upload and download + Given I go to the page + Then I upload the file "" + Then I download the converted file + + Examples: + | Verb | File | + | pdf-to-ppt | test-files/test.pdf | \ No newline at end of file diff --git a/test/e2e/frictionless/features/smoke/eventwrapper.feature b/test/e2e/frictionless/features/smoke/eventwrapper.feature new file mode 100644 index 00000000..0ed32ca3 --- /dev/null +++ b/test/e2e/frictionless/features/smoke/eventwrapper.feature @@ -0,0 +1,27 @@ +Feature: Frictionless Event Wrapper Block + + Background: + Given I have a new browser context + + @MWPW-130448 @smoke-eventwrapper + Scenario Outline: L2 Verb - Personalization events + Given I go to the page + Then I should see the default how-to + And I should see the verb subfooter + Then I upload the file "" + Then I download the converted file + + When I go to the page + Then I should see the 2nd conversion how-to + And I should see the verb subfooter + Then I upload the file "" + Then I wait for the conversion + + When I go to the page + Then I should see upsell + Then I should see the 2nd conversion how-to + And I should see the verb subfooter + + Examples: + | Verb | File | + | pdf-to-ppt | test-files/test.pdf | \ No newline at end of file diff --git a/test/e2e/frictionless/features/smoke/review.feature b/test/e2e/frictionless/features/smoke/review.feature new file mode 100644 index 00000000..2c7655d7 --- /dev/null +++ b/test/e2e/frictionless/features/smoke/review.feature @@ -0,0 +1,15 @@ +Feature: Frictionless Review Block + + Background: + Given I have a new browser context + + @MWPW-130449 @smoke-review + Scenario Outline: Review rating and stats + Given I go to the page + Then I should see the review stats + When I submit review feedback + Then I should see the review submit response + + Examples: + | Verb | + | pdf-to-ppt | \ No newline at end of file diff --git a/test/e2e/frictionless/features/verb.feature b/test/e2e/frictionless/features/verb.feature new file mode 100644 index 00000000..f03ca8c0 --- /dev/null +++ b/test/e2e/frictionless/features/verb.feature @@ -0,0 +1,60 @@ +Feature: Frictionless PDF Verbs + + Background: + Given I have a new browser context + + @pdf-to-ppt + Scenario: PDF Converter - PDF to PPT + Given I go to the pdf-to-ppt page + Then I upload the PDF "test-files/test.pdf" + Then I download the converted file + + @pdf-to-word + Scenario: PDF Converter - PDF to Word + Given I go to the pdf-to-word page + Then I upload the PDF "test-files/test.pdf" + Then I download the converted file + + @pdf-to-excel + Scenario: PDF Converter - PDF to Excel + Given I go to the pdf-to-excel page + Then I upload the PDF "test-files/test.pdf" + Then I download the converted file + + @pdf-to-png + Scenario: PDF Converter - PDF to JPG + Given I go to the pdf-to-jpg page + Then I upload the PDF "test-files/test.pdf" + Then I choose "PNG (*.png)" as the output format + Then I download the converted file + + @pdf-to-jpg + Scenario: PDF Converter - PDF to JPG + Given I go to the pdf-to-jpg page + Then I upload the PDF "test-files/test.pdf" + Then I choose "JPG (*.jpg, *.jpeg)" as the output format + Then I download the converted file + + @word-to-pdf + Scenario: PDF Converter - Word to PDF + Given I go to the word-to-pdf page + Then I upload the file "test-files/test.docx" + Then I download the converted file + + @jpg-to-pdf + Scenario: PDF Converter - JPG to PDF + Given I go to the jpg-to-pdf page + Then I upload the file "test-files/test.jpg" + Then I download the converted file + + @excel-to-pdf + Scenario: PDF Converter - Excel to PDF + Given I go to the excel-to-pdf page + Then I upload the file "test-files/test.xlsx" + Then I download the converted file + + @ppt-to-pdf + Scenario: PDF Converter - Excel to PDF + Given I go to the ppt-to-pdf page + Then I upload the file "test-files/test.pptx" + Then I download the converted file \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/addpagestopdf.page.js b/test/e2e/frictionless/page-objects/addpagestopdf.page.js new file mode 100644 index 00000000..b4798b18 --- /dev/null +++ b/test/e2e/frictionless/page-objects/addpagestopdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class AddPagesToPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/add-pages-to-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/convertpdf.page.js b/test/e2e/frictionless/page-objects/convertpdf.page.js new file mode 100644 index 00000000..ab0227a1 --- /dev/null +++ b/test/e2e/frictionless/page-objects/convertpdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class ConvertPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/convert-pdf"); + } +} diff --git a/test/e2e/frictionless/page-objects/croppdf.page.js b/test/e2e/frictionless/page-objects/croppdf.page.js new file mode 100644 index 00000000..68345b20 --- /dev/null +++ b/test/e2e/frictionless/page-objects/croppdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class CropPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/crop-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/deletepdfpages.page.js b/test/e2e/frictionless/page-objects/deletepdfpages.page.js new file mode 100644 index 00000000..fd922354 --- /dev/null +++ b/test/e2e/frictionless/page-objects/deletepdfpages.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class DeletePdfPagesPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/delete-pdf-pages"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/exceltopdf.page.js b/test/e2e/frictionless/page-objects/exceltopdf.page.js new file mode 100644 index 00000000..e79b31f4 --- /dev/null +++ b/test/e2e/frictionless/page-objects/exceltopdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class ExcelToPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/excel-to-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/extractpdfpages.page.js b/test/e2e/frictionless/page-objects/extractpdfpages.page.js new file mode 100644 index 00000000..152e09b2 --- /dev/null +++ b/test/e2e/frictionless/page-objects/extractpdfpages.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class ExtractPdfPagesPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/extract-pdf-pages"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/frictionless.page.js b/test/e2e/frictionless/page-objects/frictionless.page.js new file mode 100644 index 00000000..1a7b72dc --- /dev/null +++ b/test/e2e/frictionless/page-objects/frictionless.page.js @@ -0,0 +1,40 @@ +import { classes } from "polytype"; +import { GnavPage } from "@amwp/platform-ui-lib-adobe/lib/common/page-objects/gnav.page"; +import { PdfWidgetSection } from "./pdfwidget.section"; + +export class FrictionlessPage extends classes(GnavPage, PdfWidgetSection) { + constructor(contentPath) { + let locContentPath = contentPath; + // if locale is specified, add to the path + if (global.config.profile.locale) { + locContentPath = locContentPath.replace(/^\/*|\/*$/g, ''); + if (global.config.profile.locale === 'us') { + locContentPath = `/${locContentPath}`; + } else { + locContentPath = `/${global.config.profile.locale}/${locContentPath}`; + } + } + super({ + super: GnavPage, + arguments: [locContentPath], + }); + this.buildProps({ + howToDefault: 'div[data-path*="how-to/default"]', + howTo2ndConversion: '[data-tag="2nd conversion"] div[data-path*="how-to/2nd-conversion"]', + verbSubfooter: '.verb-subfooter', + reviewStats: '.hlx-ReviewStats', + reviewSubmitResponse: '.hlx-submitResponse', + reviewDisabled: '.hlx-Review-ratingFields[disabled]', + reviewCommentField: '.hlx-Review-commentFields textarea', + reviewCommentSubmit: '.hlx-Review-commentFields input[type="submit"]', + reviewInputField: 'fieldset.hlx-Review-ratingFields input', + signUp: '[href*="https://auth.services.adobe.com"][href*="signup"]', + extensionModal: '#chromeext', + closeExtensionModal: '#chromeext .dialog-close' + }); + } + + reviewStartInput(rating) { + return this.native.locator(`.hlx-Review-ratingFields input[value="${rating}"]`); + } +} diff --git a/test/e2e/frictionless/page-objects/jpgtopdf.page.js b/test/e2e/frictionless/page-objects/jpgtopdf.page.js new file mode 100644 index 00000000..9b713e6f --- /dev/null +++ b/test/e2e/frictionless/page-objects/jpgtopdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class JpgToPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/jpg-to-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/mergepdf.page.js b/test/e2e/frictionless/page-objects/mergepdf.page.js new file mode 100644 index 00000000..43525a06 --- /dev/null +++ b/test/e2e/frictionless/page-objects/mergepdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class MergePdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/merge-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/pdfeditor.page.js b/test/e2e/frictionless/page-objects/pdfeditor.page.js new file mode 100644 index 00000000..7d090b0c --- /dev/null +++ b/test/e2e/frictionless/page-objects/pdfeditor.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class PdfEditorPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/pdf-editor"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/pdftoexcel.page.js b/test/e2e/frictionless/page-objects/pdftoexcel.page.js new file mode 100644 index 00000000..93ab0bff --- /dev/null +++ b/test/e2e/frictionless/page-objects/pdftoexcel.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class PdfToExcelPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/pdf-to-excel"); + } +} diff --git a/test/e2e/frictionless/page-objects/pdftojpg.page.js b/test/e2e/frictionless/page-objects/pdftojpg.page.js new file mode 100644 index 00000000..4ec3885e --- /dev/null +++ b/test/e2e/frictionless/page-objects/pdftojpg.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class PdfToJpgPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/pdf-to-jpg"); + } +} diff --git a/test/e2e/frictionless/page-objects/pdftoppt.page.js b/test/e2e/frictionless/page-objects/pdftoppt.page.js new file mode 100644 index 00000000..229f9414 --- /dev/null +++ b/test/e2e/frictionless/page-objects/pdftoppt.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class PdfToPptPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/pdf-to-ppt"); + } +} diff --git a/test/e2e/frictionless/page-objects/pdftoword.page.js b/test/e2e/frictionless/page-objects/pdftoword.page.js new file mode 100644 index 00000000..f7502a47 --- /dev/null +++ b/test/e2e/frictionless/page-objects/pdftoword.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class PdfToWordPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/pdf-to-word"); + } +} diff --git a/test/e2e/frictionless/page-objects/pdfwidget.section.js b/test/e2e/frictionless/page-objects/pdfwidget.section.js new file mode 100644 index 00000000..037090a0 --- /dev/null +++ b/test/e2e/frictionless/page-objects/pdfwidget.section.js @@ -0,0 +1,46 @@ +import { Section } from "@amwp/platform-ui-automation/lib/common/page-objects/section"; + +export class PdfWidgetSection extends Section { + constructor() { + super(); + this.buildProps({ + selectButton: "#lifecycle-nativebutton", + fileUploadInput: '//input[contains(@class,"FileUpload")]', + dropZoneInput: '//input[contains(@class,"DropzoneContent")]', + downloadButton: 'button[data-test-id="download"], button[data-testid*="download"]', + filenameHeader: '//div[contains(@class, "FilenameHeader__name")]', + selectFormat: "button#select-format", + convertButton: 'button[data-test-id*="convert"]', + mergeButton: 'button[data-test-id*="merge"]', + continueWithAdobe: 'button[data-test-id="adobe-social-cta-button"]', + checkmark: 'svg[data-test-id="checkmark"]', + pdfIsReady: '[class*="ReadyText__heading___"]', + cannotDownload: 'div[class*="cannotDownload"]', + upsellWall: 'div[class^="UpsellWallSocial__upsell___"]', + oneTapPrompt: '[id="credential_picker_container"]', + dcWebDownload: 'button[aria-label="Download"]', + dcWebFnsOverlay: '[data-testid="fns-overlay"]', + dcWebHome: '[href*="/link/home"]', + dcWebDocumentsTab: '//div[@role="tab"]//span[text()="Documents"]/..', + dcWebCheckAllFiles: '//div[contains(@class, "Files")]//input[@title="Select All"]', + dcWebDelete: '//button[@data-test-id="delete-action-button"]', + }); + } + + imageFormatItem(format) { + return this.native.locator(`//div[@role="option"]//span[text()="${format}"]/..`); + } + + async uploadFiles(filePaths) { + await this.fileUploadInput.setInputFiles(filePaths); + } + + async download() { + await this.downloadButton.click({ timeout: 180000 }); + } + + async selectImageFormat(format) { + await this.selectFormat.click(); + await this.imageFormatItem(format).click(); + } +} diff --git a/test/e2e/frictionless/page-objects/ppttopdf.page.js b/test/e2e/frictionless/page-objects/ppttopdf.page.js new file mode 100644 index 00000000..bbcfd8c5 --- /dev/null +++ b/test/e2e/frictionless/page-objects/ppttopdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class PptToPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/ppt-to-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/rearrangepdf.page.js b/test/e2e/frictionless/page-objects/rearrangepdf.page.js new file mode 100644 index 00000000..aec7fa3d --- /dev/null +++ b/test/e2e/frictionless/page-objects/rearrangepdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class RearrangePdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/rearrange-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/requestsignature.page.js b/test/e2e/frictionless/page-objects/requestsignature.page.js new file mode 100644 index 00000000..96071a5b --- /dev/null +++ b/test/e2e/frictionless/page-objects/requestsignature.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class RequestSignaturePage extends FrictionlessPage { + constructor() { + super("/acrobat/online/request-signature"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/rotatepdf.page.js b/test/e2e/frictionless/page-objects/rotatepdf.page.js new file mode 100644 index 00000000..494867b3 --- /dev/null +++ b/test/e2e/frictionless/page-objects/rotatepdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class RotatePdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/rotate-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/signpdf.page.js b/test/e2e/frictionless/page-objects/signpdf.page.js new file mode 100644 index 00000000..91de7a1b --- /dev/null +++ b/test/e2e/frictionless/page-objects/signpdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class SignPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/sign-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/splitpdf.page.js b/test/e2e/frictionless/page-objects/splitpdf.page.js new file mode 100644 index 00000000..7005fef8 --- /dev/null +++ b/test/e2e/frictionless/page-objects/splitpdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class SplitPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/split-pdf"); + } +} \ No newline at end of file diff --git a/test/e2e/frictionless/page-objects/wordtopdf.page.js b/test/e2e/frictionless/page-objects/wordtopdf.page.js new file mode 100644 index 00000000..450e1b8d --- /dev/null +++ b/test/e2e/frictionless/page-objects/wordtopdf.page.js @@ -0,0 +1,7 @@ +import { FrictionlessPage } from './frictionless.page'; + +export class WordToPdfPage extends FrictionlessPage { + constructor() { + super("/acrobat/online/word-to-pdf"); + } +} diff --git a/test/e2e/frictionless/profiles.yml b/test/e2e/frictionless/profiles.yml new file mode 100644 index 00000000..df973c2d --- /dev/null +++ b/test/e2e/frictionless/profiles.yml @@ -0,0 +1,14 @@ +--- +default: -p prod -b chromium --headless false --logConsole + +prod: + baseUrl: https://www.adobe.com + +stage: + baseUrl: https://www.stage.adobe.com + +live: + baseUrl: https://${branch}--dc--adobecom.hlx.live + +preview: + baseUrl: https://${branch}--dc--adobecom.hlx.page \ No newline at end of file diff --git a/test/e2e/frictionless/step-definitions/common.steps.js b/test/e2e/frictionless/step-definitions/common.steps.js new file mode 100644 index 00000000..3bd3c02e --- /dev/null +++ b/test/e2e/frictionless/step-definitions/common.steps.js @@ -0,0 +1,32 @@ +const { request } = require('@playwright/test'); +import { Then } from "@cucumber/cucumber"; + +Then(/^I load test data from sharepoint "([^\"]*)" under this path "([^\"]*)"$/, async function (url, path) { + const context = await request.newContext({ baseURL: url }); + const res = await context.fetch(path); + this.page.testData = await res.json(); +}); + +Then(/^I enable network logging$/, async function () { + let networklogs = []; + this.networklogs = networklogs; + console.log('Before all tests: Enable network logging'); + // Enable network logging + await this.page.native.route('**', (route) => { + const url = route.request().url(); + if (url.includes('sstats.adobe.com/ee/or2/v1/interact') || url.includes('sstats.adobe.com/ee/or2/v1/collect')) { + networklogs.push(url); + // eslint-disable-next-line max-len, no-underscore-dangle + networklogs.push(JSON.stringify(route.request().postDataJSON().events[0].data._adobe_corpnew.digitalData.primaryEvent)); + } + route.continue(); + }); +}); + +Then(/^I disable network logging$/, async function () { + console.log(this.networklogs); + console.log('After all tests: Disable network logging'); + // Disable network logging + await this.page.native.unroute('**'); + await this.page.native.close(); +}); \ No newline at end of file diff --git a/test/e2e/frictionless/step-definitions/dc.steps.js b/test/e2e/frictionless/step-definitions/dc.steps.js new file mode 100644 index 00000000..178a5ef0 --- /dev/null +++ b/test/e2e/frictionless/step-definitions/dc.steps.js @@ -0,0 +1,241 @@ +import { Then } from "@cucumber/cucumber"; +import { PdfToPptPage } from "../page-objects/pdftoppt.page"; +import { PdfToWordPage } from "../page-objects/pdftoword.page"; +import { PdfToExcelPage } from "../page-objects/pdftoexcel.page"; +import { PdfToJpgPage } from "../page-objects/pdftojpg.page"; +import { WordToPdfPage } from "../page-objects/wordtopdf.page"; +import { JpgToPdfPage } from "../page-objects/jpgtopdf.page"; +import { ExcelToPdfPage } from "../page-objects/exceltopdf.page"; +import { PptToPdfPage } from "../page-objects/ppttopdf.page"; +import { ConvertPdfPage } from "../page-objects/convertpdf.page"; +import { SignPdfPage } from "../page-objects/signpdf.page"; +import { RequestSignaturePage } from "../page-objects/requestsignature.page"; +import { CropPdfPage } from "../page-objects/croppdf.page"; +import { DeletePdfPagesPage } from "../page-objects/deletepdfpages.page"; +import { RotatePdfPage } from "../page-objects/rotatepdf.page"; +import { RearrangePdfPage } from "../page-objects/rearrangepdf.page"; +import { SplitPdfPage } from "../page-objects/splitpdf.page"; +import { AddPagesToPdfPage } from "../page-objects/addpagestopdf.page"; +import { ExtractPdfPagesPage } from "../page-objects/extractpdfpages.page"; +import { PdfEditorPage } from "../page-objects/pdfeditor.page"; +import { MergePdfPage } from "../page-objects/mergepdf.page"; +import { FrictionlessPage } from "../page-objects/frictionless.page"; +import { expect } from "@playwright/test"; +const path = require("path"); +const fs = require("fs"); + +async function enableNetworkLogging(page) { + if (global.config.profile.enableAnalytics) { + let networklogs = []; + page.networklogs = networklogs; + console.log('Before all tests: Enable network logging'); + // Enable network logging + await page.native.route('**', (route) => { + const url = route.request().url(); + networklogs.push(route.request()); + route.continue(); + }); + } +} + +Then(/^I have a new browser context$/, async function () { + PW.context = await PW.browser.newContext(PW.contextOptions); +}); + +Then(/^I go to the ([^\"]*) page$/, async function (verb) { + const pageClass = { + "pdf-to-ppt": PdfToPptPage, + "pdf-to-word": PdfToWordPage, + "pdf-to-excel": PdfToExcelPage, + "pdf-to-jpg": PdfToJpgPage, + "word-to-pdf": WordToPdfPage, + "jpg-to-pdf": JpgToPdfPage, + "excel-to-pdf": ExcelToPdfPage, + "ppt-to-pdf": PptToPdfPage, + "convert-pdf": ConvertPdfPage, + "sign-pdf": SignPdfPage, + "request-signature": RequestSignaturePage, + "crop-pdf": CropPdfPage, + "delete-pdf-pages": DeletePdfPagesPage, + "rotate-pdf": RotatePdfPage, + "rearrange-pdf": RearrangePdfPage, + "split-pdf": SplitPdfPage, + "add-pages-to-pdf": AddPagesToPdfPage, + "extract-pdf-pages": ExtractPdfPagesPage, + "pdf-editor": PdfEditorPage, + "merge-pdf": MergePdfPage, + }[verb]; + this.page = new pageClass(); + + this.page.beforeOpen = enableNetworkLogging; + + await this.page.open(); +}); + +Then(/^I upload the (?:PDF|file|files) "([^\"]*)"$/, async function (filePath) { + this.context(FrictionlessPage); + const filePaths = filePath.split(","); + const absPaths = filePaths.map((x) => + path.resolve(global.config.profile.site, x) + ); + await expect(this.page.selectButton).toHaveCount(1, { timeout: 15000 }); + await this.page.native.waitForTimeout(2000); + await this.page.uploadFiles(absPaths); +}); + +Then(/^I download the converted file$/, { timeout: 200000 }, async function () { + this.context(FrictionlessPage); + await this.page.downloadButton.waitFor({ timeout: 180000 }); + + let convertedName = await this.page.filenameHeader.getAttribute("title"); + + // Prepare waiting for the download event + const downloadPromise = this.page.native.waitForEvent("download"); + + this.page.download(); + + // Behavior diff: + // Playwright downloads the file to a temp dir with a UUID file name. + // Chrome downloads to Downloads dir with the new extension of + // the original file name. + const download = await downloadPromise; + console.log("Downloaded file: " + (await download.path())); + let saveAsName = path.resolve( + require("os").homedir(), + "Downloads", + convertedName + ); + await download.saveAs(saveAsName); + console.log(`Saved as ${saveAsName}`); +}); + +Then(/^I choose "([^\"]*)" as the output format$/, async function (format) { + this.context(FrictionlessPage); + await this.page.selectFormat.waitFor({ timeout: 10000 }); + await this.page.selectImageFormat(format); + await this.page.convertButton.click(); +}); + +Then(/^I merge the uploaded files$/, async function () { + this.context(FrictionlessPage); + await this.page.mergeButton.click({ timeout: 120000 }); +}); + +Then(/^I should not see any browser console errors$/, async function () { + if (this.page.consoleMessages) { + const errors = this.page.consoleMessages.filter( + (x) => x.type() === "error" + ); + for (let error of errors) { + console.log(error.text()); + } + expect(errors).toHaveLength(0); + } +}); + +Then(/^I continue with AdobeID$/, { timeout: 120000 }, async function () { + await this.page.continueWithAdobe.click({ timeout: 100000 }); +}); + +Then(/^I wait for the conversion$/, { timeout: 180000 }, async function () { + await expect(this.page.pdfIsReady).toBeVisible({ timeout: 150000 }); +}); + +Then(/^I should see the default how-to$/, async function () { + await expect(this.page.howToDefault).toBeVisible(); +}); + +Then(/^I should see upsell$/, async function () { + await expect(this.page.upsellWall).toHaveCount(1, { timeout: 10000 }); +}); + +Then(/^I should see the 2nd conversion how-to$/, async function () { + await expect(this.page.howTo2ndConversion).toBeVisible({ timeout: 10000 }); +}); + +Then(/^I should see the verb subfooter$/, async function () { + await expect(this.page.verbSubfooter).toBeVisible({ timeout: 10000 }); + const verbCount = await this.page.verbSubfooter.locator("a").count(); + expect(verbCount).toBeGreaterThan(20); +}); + +Then(/^I submit review feedback$/, async function () { + this.context(FrictionlessPage); + await this.page.reviewStartInput(3).click({timeout: 5000}); + await this.page.reviewCommentField.fill("Test"); + await this.page.reviewStartInput(5).click(); + await this.page.reviewCommentSubmit.click(); +}); + +Then(/^I should see the review stats$/, async function () { + this.context(FrictionlessPage); + await expect(this.page.reviewStats).toBeVisible({timeout: 5000}); +}); + +Then(/^I should see the review submit response$/, async function () { + this.context(FrictionlessPage); + await expect(this.page.reviewSubmitResponse).toBeVisible({timeout: 5000}); +}); + +Then(/^I download the pdf from DC web$/, async function () { + this.context(FrictionlessPage); + await this.page.dcWebDownload.waitFor({ timeout: 100000 }); + const downloadPromise = this.page.native.waitForEvent("download"); + await this.page.dcWebDownload.click(); + const download = await downloadPromise; + console.log("Downloaded file: " + (await download.path())); +}); + +Then(/^I login to Google$/, async function () { + let username = "//input[@type='email']"; + let pw = "//input[@type='password'][@aria-label='Enter your password']"; + + await this.page.native.locator(username).waitFor(); + await this.page.native.locator(username).fill(process.env.ADOBEID_USERNAME); + await this.page.native.locator(username).press('Enter'); + await this.page.native.waitForTimeout(2000); + await this.page.native.locator(pw).waitFor(); + await this.page.native.locator(pw).fill(process.env.ADOBEID_PASSWORD); + await this.page.native.locator(pw).press('Enter'); +}); + +Then(/^I should see the Google credential picker$/, async function () { + await expect(this.page.oneTapPrompt).toBeVisible(); +}); + +Then(/^I click the Continue button inside the Google iFrame$/, async function () { + const element = await this.page.native.frameLocator("iframe[src*='https://accounts.google.com/gsi/iframe']").getByText("Continue as"); + await element.waitFor(); + await element.click(); +}); + +Then(/^I should see the file in DC Web$/, async function () { + await expect(this.page.dcWebFnsOverlay).toBeVisible({timeout: 30000}); +}); + +Then(/^I click the element "([^\"]*)"$/, async function (selector) { + await this.page.native.locator(selector).click(); +}); + +Then(/^I should see the element "([^\"]*)"$/, async function (selector) { + await this.page.native.locator(selector).waitFor(); +}); + +Then(/^I delete the file in DC Web$/, async function () { + await this.page.dcWebHome.click(); + await this.page.dcWebDocumentsTab.click(); + await this.page.dcWebCheckAllFiles.click(); + await this.page.dcWebDelete.click(); +}); + +Then(/^I should (|not )see a modal promoting the browser extension$/, { timeout: 180000 }, async function (neg) { + if (neg) { + await expect(this.page.extensionModal).not.toBeVisible(); + } else { + await expect(this.page.extensionModal).toBeVisible(); + } +}); + +Then(/^I dismiss the extension modal$/, async function () { + await this.page.closeExtensionModal.click(); +}); \ No newline at end of file diff --git a/test/e2e/frictionless/test-files/test.docx b/test/e2e/frictionless/test-files/test.docx new file mode 100644 index 00000000..f62e237c Binary files /dev/null and b/test/e2e/frictionless/test-files/test.docx differ diff --git a/test/e2e/frictionless/test-files/test.jpg b/test/e2e/frictionless/test-files/test.jpg new file mode 100644 index 00000000..69dd9bc2 Binary files /dev/null and b/test/e2e/frictionless/test-files/test.jpg differ diff --git a/test/e2e/frictionless/test-files/test.pdf b/test/e2e/frictionless/test-files/test.pdf new file mode 100644 index 00000000..1daa2cc2 Binary files /dev/null and b/test/e2e/frictionless/test-files/test.pdf differ diff --git a/test/e2e/frictionless/test-files/test.pptx b/test/e2e/frictionless/test-files/test.pptx new file mode 100644 index 00000000..55e7df70 Binary files /dev/null and b/test/e2e/frictionless/test-files/test.pptx differ diff --git a/test/e2e/frictionless/test-files/test.xlsx b/test/e2e/frictionless/test-files/test.xlsx new file mode 100644 index 00000000..705335cc Binary files /dev/null and b/test/e2e/frictionless/test-files/test.xlsx differ diff --git a/test/e2e/frictionless/test-files/test2.pdf b/test/e2e/frictionless/test-files/test2.pdf new file mode 100644 index 00000000..c7917e51 Binary files /dev/null and b/test/e2e/frictionless/test-files/test2.pdf differ