diff --git a/packages/playwright/index.js b/packages/playwright/index.js new file mode 100644 index 0000000..3a034cb --- /dev/null +++ b/packages/playwright/index.js @@ -0,0 +1,5 @@ +const { smartuiSnapshot } = require('./src/smartui'); + +module.exports = { + smartuiSnapshot +} \ No newline at end of file diff --git a/packages/playwright/package.json b/packages/playwright/package.json new file mode 100644 index 0000000..5ecea02 --- /dev/null +++ b/packages/playwright/package.json @@ -0,0 +1,38 @@ +{ + "name": "@lambdatest/playwright-driver", + "version": "1.0.3", + "description": "Playwright SDK for smart UI", + "main": "index.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/LambdaTest/lambdatest-js-sdk.git", + "directory": "packages/playwright" + }, + "keywords": [ + "lambdatest", + "playwright", + "smartui" + ], + "author": "LambdaTest ", + "license": "MIT", + "bugs": { + "url": "https://github.com/LambdaTest/lambdatest-js-sdk/issues" + }, + "homepage": "https://github.com/LambdaTest/lambdatest-js-sdk#readme", + + "peerDependencies": { + "playwright-core": ">=1" + }, + "devDependencies": { + "@playwright/test": "^1.24.2", + "playwright": "^1.24.2" + }, + "dependencies": { + "@lambdatest/sdk-utils": "workspace:^" + } + + } + \ No newline at end of file diff --git a/packages/playwright/src/smartui.js b/packages/playwright/src/smartui.js new file mode 100644 index 0000000..dee3068 --- /dev/null +++ b/packages/playwright/src/smartui.js @@ -0,0 +1,42 @@ +const utils = require('@lambdatest/sdk-utils'); +const pkgName = require('../package.json').name; + +// Take a DOM snapshot and post it to the snapshot endpoint +async function smartuiSnapshot(page, name, options) { + if (!page) throw new Error('A Playwright `page` object is required.'); + if (!name || typeof name !== 'string') throw new Error('The `name` argument is required.'); + if (!(await utils.isSmartUIRunning())) throw new Error('Cannot find SmartUI server.'); + + let log = utils.logger(pkgName); + + try { + // Inject the DOM serialization script + const resp = await utils.fetchDOMSerializer(); + await page.evaluate(resp.body.data.dom); + + // Serialize and capture the DOM + /* istanbul ignore next: no instrumenting injected code */ + let { dom } = await page.evaluate((options) => ({ + /* eslint-disable-next-line no-undef */ + dom: SmartUIDOM.serialize(options) + }), {}); + + // Post the DOM to the snapshot endpoint with snapshot options and other info + let { body } = await utils.postSnapshot({ + dom, + url: page.url(), + name, + options + }, pkgName); + + log.info(`Snapshot captured: ${name}`); + + if (body && body.data && body.data.warnings?.length !== 0) body.data.warnings.map(e => log.warn(e)); + } catch (err) { + throw err; + } +} + +module.exports = { + smartuiSnapshot +} \ No newline at end of file diff --git a/packages/puppeteer/index.js b/packages/puppeteer/index.js new file mode 100644 index 0000000..35f348a --- /dev/null +++ b/packages/puppeteer/index.js @@ -0,0 +1,5 @@ +const { smartuiSnapshot } = require('./src/smartui'); + +module.exports = { + smartuiSnapshot +} diff --git a/packages/puppeteer/package.json b/packages/puppeteer/package.json new file mode 100644 index 0000000..f302dd8 --- /dev/null +++ b/packages/puppeteer/package.json @@ -0,0 +1,28 @@ +{ + "name": "@lambdatest/puppeteer-driver", + "version": "1.0.3", + "description": "Puppeteer SDK for smart UI", + "main": "index.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1" + }, + "repository": { + "type": "git", + "url": "git+https://github.com/LambdaTest/lambdatest-js-sdk.git", + "directory": "packages/puppeteer" + }, + "keywords": [ + "lambdatest", + "puppeteer", + "smartui" + ], + "author": "LambdaTest ", + "license": "MIT", + "bugs": { + "url": "https://github.com/LambdaTest/lambdatest-js-sdk/issues" + }, + "homepage": "https://github.com/LambdaTest/lambdatest-js-sdk#readme", + "dependencies": { + "@lambdatest/sdk-utils": "workspace:^" + } +} diff --git a/packages/puppeteer/src/smartui.js b/packages/puppeteer/src/smartui.js new file mode 100644 index 0000000..4072d36 --- /dev/null +++ b/packages/puppeteer/src/smartui.js @@ -0,0 +1,44 @@ +const utils = require('@lambdatest/sdk-utils'); +const pkgName = require('../package.json').name; + + +async function smartuiSnapshot(page, name, options = {}) { + if (!page) throw new Error('puppeteer `page` argument is required.'); + if (!name || typeof name !== 'string') throw new Error('The `name` argument is required.'); + if (!(await utils.isSmartUIRunning())) throw new Error('Cannot find SmartUI server.'); + + let log = utils.logger(pkgName); + + try { + // Fetch the DOM serializer from the SmartUI server. + let resp = await utils.fetchDOMSerializer(); + + // Inject the DOM serializer into the page. + await page.evaluate(resp.body.data.dom); + + // Serialize the DOM + let { dom, url } = await page.evaluate(options => ({ + dom: SmartUIDOM.serialize(options), + url: document.URL + }), {}); + + + // Post it to the SmartUI server. + let { body } = await utils.postSnapshot({ + dom, + url, + name, + options + }, pkgName); + + log.info(`Snapshot captured: ${name}`); + + if (body && body.data && body.data.warnings?.length !== 0) body.data.warnings.map(e => log.warn(e)); + } catch (error) { + throw new Error(error); + } +} + +module.exports = { + smartuiSnapshot +}; \ No newline at end of file diff --git a/packages/sdk-utils/package.json b/packages/sdk-utils/package.json index b08c71d..053b186 100644 --- a/packages/sdk-utils/package.json +++ b/packages/sdk-utils/package.json @@ -1,6 +1,6 @@ { "name": "@lambdatest/sdk-utils", - "version": "1.0.2", + "version": "1.0.3", "description": "", "main": "index.js", "repository": { diff --git a/packages/sdk-utils/src/lib/utils.js b/packages/sdk-utils/src/lib/utils.js index 1e43008..8fc031a 100644 --- a/packages/sdk-utils/src/lib/utils.js +++ b/packages/sdk-utils/src/lib/utils.js @@ -1,5 +1,6 @@ function getSmartUIServerAddress() { - return process.env.SMARTUI_SERVER_ADDRESS || 'http://localhost:8080' + if (!process.env.SMARTUI_SERVER_ADDRESS) throw new Error('SmartUI server address not found'); + return process.env.SMARTUI_SERVER_ADDRESS } module.exports = { diff --git a/packages/selenium-driver/package.json b/packages/selenium-driver/package.json index 9a47669..53898da 100644 --- a/packages/selenium-driver/package.json +++ b/packages/selenium-driver/package.json @@ -1,6 +1,6 @@ { "name": "@lambdatest/selenium-driver", - "version": "1.0.2", + "version": "1.0.3", "description": "Selenium driver for all Lambdatest functionalities", "main": "index.js", "repository": { diff --git a/packages/selenium-driver/src/smartui.js b/packages/selenium-driver/src/smartui.js index a2b3803..a2d34fc 100644 --- a/packages/selenium-driver/src/smartui.js +++ b/packages/selenium-driver/src/smartui.js @@ -4,8 +4,8 @@ const pkgName = require('../package.json').name; async function smartuiSnapshot(driver, name, options = {}) { // TODO: check if driver is selenium webdriver object if (!driver) throw new Error('An instance of the selenium driver object is required.'); - if (!name) throw new Error('The `name` argument is required.'); - if (!(await utils.isSmartUIRunning())) throw new Error('SmartUI server is not running.'); + if (!name || typeof name !== 'string') throw new Error('The `name` argument is required.'); + if (!(await utils.isSmartUIRunning())) throw new Error('Cannot find SmartUI server.'); let log = utils.logger(pkgName); try { diff --git a/packages/testcafe/index.js b/packages/testcafe/index.js new file mode 100644 index 0000000..3a034cb --- /dev/null +++ b/packages/testcafe/index.js @@ -0,0 +1,5 @@ +const { smartuiSnapshot } = require('./src/smartui'); + +module.exports = { + smartuiSnapshot +} \ No newline at end of file diff --git a/packages/testcafe/package.json b/packages/testcafe/package.json new file mode 100644 index 0000000..02c92a2 --- /dev/null +++ b/packages/testcafe/package.json @@ -0,0 +1,35 @@ +{ + "name": "@lambdatest/testcafe-driver", + "version": "1.0.3", + "description": "Testcafe SDK for LambdaTest smart UI", + "repository": { + "type": "git", + "url": "git+https://github.com/LambdaTest/lambdatest-js-sdk.git", + "directory": "packages/testcafe" + }, + "main": "index.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1" + }, + "keywords": [ + "lambdatest", + "testcafe", + "smartui" + ], + "author": "LambdaTest ", + "license": "MIT", + "bugs": { + "url": "https://github.com/LambdaTest/lambdatest-js-sdk/issues" + }, + + "homepage": "https://github.com/LambdaTest/lambdatest-js-sdk#readme", + "devDependencies": { + "testcafe": "^3.4.0" + }, + "peerDependencies": { + "testcafe": ">=1" + }, + "dependencies": { + "@lambdatest/sdk-utils": "workspace:^" + } +} diff --git a/packages/testcafe/src/smartui.js b/packages/testcafe/src/smartui.js new file mode 100644 index 0000000..3a57b2c --- /dev/null +++ b/packages/testcafe/src/smartui.js @@ -0,0 +1,44 @@ +const utils = require('@lambdatest/sdk-utils'); +const pkgName = require('../package.json').name; + +async function smartuiSnapshot(t, name, options) { + if (!t) throw new Error("The test function's `t` argument is required."); + if (!name || typeof name !== 'string') throw new Error('The `name` argument is required.'); + if (!(await utils.isSmartUIRunning())) throw new Error('Cannot find SmartUI server.'); + + let log = utils.logger(pkgName); + + try { + // Inject the DOM serialization script + /* eslint-disable-next-line no-new-func */ + const resp = await utils.fetchDOMSerializer(); + + await t.eval(new Function(resp.body.data.dom), { boundTestRun: t }); + + // Serialize and capture the DOM + /* istanbul ignore next: no instrumenting injected code */ + let { dom, url } = await t.eval((options) => ({ + /* eslint-disable-next-line no-undef */ + dom: SmartUIDOM.serialize(options), + url: window.location.href || document.URL, + }), { boundTestRun: t, dependencies: {} }); + + let { body } = await utils.postSnapshot({ + dom: dom, + url, + name, + options + }, pkgName); + + log.info(`Snapshot captured: ${name}`); + + if (body && body.data && body.data.warnings?.length !== 0) body.data.warnings.map(e => log.warn(e)); + } catch (error) { + // Handle errors + throw error; + } +} + +module.exports = { + smartuiSnapshot +} \ No newline at end of file